@nyaruka/temba-components 0.166.0 → 0.167.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +6 -0
- package/dist/temba-components.js +5 -3
- package/dist/temba-components.js.map +1 -1
- package/package.json +1 -1
- package/src/list/ContactList.ts +38 -7
package/CHANGELOG.md
CHANGED
|
@@ -4,8 +4,14 @@ All notable changes to this project will be documented in this file. Dates are d
|
|
|
4
4
|
|
|
5
5
|
Generated by [`auto-changelog`](https://github.com/CookPete/auto-changelog).
|
|
6
6
|
|
|
7
|
+
#### [v0.167.0](https://github.com/nyaruka/temba-components/compare/v0.166.0...v0.167.0)
|
|
8
|
+
|
|
9
|
+
- Add urn-label attribute to contact list [`#1068`](https://github.com/nyaruka/temba-components/pull/1068)
|
|
10
|
+
|
|
7
11
|
#### [v0.166.0](https://github.com/nyaruka/temba-components/compare/v0.165.0...v0.166.0)
|
|
8
12
|
|
|
13
|
+
> 22 July 2026
|
|
14
|
+
|
|
9
15
|
- Add typing indicators to contact chat [`#1064`](https://github.com/nyaruka/temba-components/pull/1064)
|
|
10
16
|
- Consume realtime notifications from the socket instead of polling [`#1063`](https://github.com/nyaruka/temba-components/pull/1063)
|
|
11
17
|
|
package/dist/temba-components.js
CHANGED
|
@@ -10679,17 +10679,19 @@ const{I:Kh}=lt,Yh=t=>t,Gh=()=>document.createComment(""),Xh=(t,e,i)=>{const o=t.
|
|
|
10679
10679
|
color: var(--text-3);
|
|
10680
10680
|
font-size: 12.5px;
|
|
10681
10681
|
}
|
|
10682
|
-
`}constructor(){super(),this.fieldsEndpoint="/api/v2/fields.json",this.featuredFields=[],this.valueKey="uuid",this.emptyMessage="No contacts",this.searchPlaceholder="Search contacts",this.columns=this.buildColumns(),this.bulkActions=[{key:"send",label:"Send",icon:Io.compose},{key:"flow",label:"Start flow",icon:Io.flow},{key:"label",label:"Group",icon:Io.group,labelsEndpoint:"/api/v2/groups.json?manual_only=1",labelsKey:"groups"},{key:"archive",label:"Archive",icon:Io.archive},{key:"delete",label:"Delete",icon:Io.delete,destructive:!0}]}connectedCallback(){super.connectedCallback(),this.loadFields()}disconnectedCallback(){this.pendingFieldsController&&(this.pendingFieldsController.abort(),this.pendingFieldsController=void 0),super.disconnectedCallback()}updated(t){super.updated(t),t.has("fieldsEndpoint")&&this.fieldsEndpoint&&this.loadFields()}async loadFields(){var t;if(!this.fieldsEndpoint)return;this.pendingFieldsController&&this.pendingFieldsController.abort();const e=new AbortController;this.pendingFieldsController=e;try{const i=await fe(this.fieldsEndpoint,e);if(this.pendingFieldsController!==e)return;const o=(null===(t=i.json)||void 0===t?void 0:t.results)||[];this.featuredFields=o.filter(t=>t.featured).sort((t,e)=>{var i,o;return(null!==(i=e.priority)&&void 0!==i?i:0)-(null!==(o=t.priority)&&void 0!==o?o:0)}),this.columns=this.buildColumns()}catch(t){"AbortError"!==(null==t?void 0:t.name)&&console.error("failed to fetch contact fields",t)}finally{this.pendingFieldsController===e&&(this.pendingFieldsController=void 0)}}buildColumns(){const t=(this.featuredFields||[]).map(t=>({key:Tp+t.key,label:t.name||t.label||t.key,sortable:!0,maxWidth:"200px"}));return[{key:"name",label:"Name",minWidth:"150px",maxWidth:"260px",pinned:!0},{key:"urn",label:"URN",minWidth:"120px",maxWidth:"190px"},...t,{key:"last_seen_on",label:"Last seen",sortable:!0,minWidth:"96px",maxWidth:"150px",align:"right"},{key:"created_on",label:"Created on",sortable:!0,minWidth:"96px",maxWidth:"150px",align:"right"}]}getRowIcon(t){return Io.contact}getRowHref(t){return(null==t?void 0:t.uuid)?`/contact/read/${t.uuid}/`:null}renderCell(t,e){var i;if(e.key.startsWith(Tp)){const o=e.key.substring(6),s=null===(i=t.fields)||void 0===i?void 0:i[o];if(null==s||""===s)return Ap;if(this.isLocationField(o)){const t=String(s);return Z`<span title=${t}>${this.locationLeaf(t)}</span>`}if(this.isDateField(o))return Z`<temba-date value=${s} display="timedate"></temba-date>`;const n=String(s);return Z`<span title=${n}>${n}</span>`}switch(e.key){case"name":return Z`<span class="contact-name" title=${t.name||""}
|
|
10682
|
+
`}constructor(){super(),this.fieldsEndpoint="/api/v2/fields.json",this.anon=!1,this.featuredFields=[],this.valueKey="uuid",this.emptyMessage="No contacts",this.searchPlaceholder="Search contacts",this.columns=this.buildColumns(),this.bulkActions=[{key:"send",label:"Send",icon:Io.compose},{key:"flow",label:"Start flow",icon:Io.flow},{key:"label",label:"Group",icon:Io.group,labelsEndpoint:"/api/v2/groups.json?manual_only=1",labelsKey:"groups"},{key:"archive",label:"Archive",icon:Io.archive},{key:"delete",label:"Delete",icon:Io.delete,destructive:!0}]}connectedCallback(){super.connectedCallback(),this.loadFields()}disconnectedCallback(){this.pendingFieldsController&&(this.pendingFieldsController.abort(),this.pendingFieldsController=void 0),super.disconnectedCallback()}willUpdate(t){super.willUpdate(t),t.has("anon")&&(this.columns=this.buildColumns())}updated(t){super.updated(t),t.has("fieldsEndpoint")&&this.fieldsEndpoint&&this.loadFields()}async loadFields(){var t;if(!this.fieldsEndpoint)return;this.pendingFieldsController&&this.pendingFieldsController.abort();const e=new AbortController;this.pendingFieldsController=e;try{const i=await fe(this.fieldsEndpoint,e);if(this.pendingFieldsController!==e)return;const o=(null===(t=i.json)||void 0===t?void 0:t.results)||[];this.featuredFields=o.filter(t=>t.featured).sort((t,e)=>{var i,o;return(null!==(i=e.priority)&&void 0!==i?i:0)-(null!==(o=t.priority)&&void 0!==o?o:0)}),this.columns=this.buildColumns()}catch(t){"AbortError"!==(null==t?void 0:t.name)&&console.error("failed to fetch contact fields",t)}finally{this.pendingFieldsController===e&&(this.pendingFieldsController=void 0)}}buildColumns(){const t=(this.featuredFields||[]).map(t=>({key:Tp+t.key,label:t.name||t.label||t.key,sortable:!0,maxWidth:"200px"}));return[{key:"name",label:"Name",minWidth:"150px",maxWidth:"260px",pinned:!0},this.anon?{key:"ref",label:"Ref",minWidth:"120px",maxWidth:"190px"}:{key:"urn",label:"URN",minWidth:"120px",maxWidth:"190px"},...t,{key:"last_seen_on",label:"Last seen",sortable:!0,minWidth:"96px",maxWidth:"150px",align:"right"},{key:"created_on",label:"Created on",sortable:!0,minWidth:"96px",maxWidth:"150px",align:"right"}]}getRowIcon(t){return Io.contact}getRowHref(t){return(null==t?void 0:t.uuid)?`/contact/read/${t.uuid}/`:null}renderCell(t,e){var i;if(e.key.startsWith(Tp)){const o=e.key.substring(6),s=null===(i=t.fields)||void 0===i?void 0:i[o];if(null==s||""===s)return Ap;if(this.isLocationField(o)){const t=String(s);return Z`<span title=${t}>${this.locationLeaf(t)}</span>`}if(this.isDateField(o))return Z`<temba-date value=${s} display="timedate"></temba-date>`;const n=String(s);return Z`<span title=${n}>${n}</span>`}switch(e.key){case"name":return Z`<span class="contact-name" title=${t.name||""}
|
|
10683
10683
|
>${t.name||Ap}</span
|
|
10684
10684
|
>`;case"urn":return Z`<span class="contact-urn"
|
|
10685
10685
|
>${this.primaryUrn(t)||Ap}</span
|
|
10686
|
+
>`;case"ref":return Z`<span class="contact-urn"
|
|
10687
|
+
>${t.ref||Ap}</span
|
|
10686
10688
|
>`;case"last_seen_on":return t.last_seen_on?Z`<temba-date
|
|
10687
10689
|
value=${t.last_seen_on}
|
|
10688
10690
|
display="timedate"
|
|
10689
10691
|
></temba-date>`:Ap;case"created_on":return t.created_on?Z`<temba-date
|
|
10690
10692
|
value=${t.created_on}
|
|
10691
10693
|
display="timedate"
|
|
10692
|
-
></temba-date>`:Ap;default:return super.renderCell(t,e)}}isDateField(t){const e=(this.featuredFields||[]).find(e=>e.key===t),i=null==e?void 0:e.value_type;return"datetime"===i||"date"===i}isLocationField(t){const e=(this.featuredFields||[]).find(e=>e.key===t),i=null==e?void 0:e.value_type;return"state"===i||"district"===i||"ward"===i}locationLeaf(t){const e=t.split(">");return e[e.length-1].trim()}primaryUrn(t){const e=t;if(e.urn)return e.urn;if(Array.isArray(e.urns)&&e.urns.length>0){const t=e.urns[0];return"string"==typeof t?t.split(":")[1]||t:(null==t?void 0:t.display)||(null==t?void 0:t.path)||""}return""}}i([ft({type:String,attribute:"fields-endpoint"})],Dp.prototype,"fieldsEndpoint",void 0),i([vt()],Dp.prototype,"featuredFields",void 0);const Mp={text:"Text",numeric:"Number",number:"Number",datetime:"Date & Time",state:"State",ward:"Ward",district:"District"},Pp=t=>Mp[t.value_type]||t.value_type||"",zp=(t,e)=>{if(!e)return!0;return[t.label,t.key,Pp(t)].join(" ").toLowerCase().indexOf(e.toLowerCase())>-1};class Ip extends Vh{constructor(){super(...arguments),this.headerTitle="",this.contentMenuEndpoint="",this.detailEndpoint="",this.otherFieldKeys=[],this.query="",this.searchOpen=!1,this.detailField=null,this.detail=null,this.prepareGhost=t=>{t.style.margin="0",t.style.boxSizing="border-box",t.style.background="var(--surface, #fff)",t.style.border="1px solid var(--border, #e4e7ec)",t.style.borderRadius="var(--curvature, 6px)",t.style.boxShadow="var(--shadow-1, 0 2px 6px rgba(0, 0, 0, 0.12))"},this.handleDetailClosed=()=>{this.detailField=null}}static get styles(){return d`
|
|
10694
|
+
></temba-date>`:Ap;default:return super.renderCell(t,e)}}isDateField(t){const e=(this.featuredFields||[]).find(e=>e.key===t),i=null==e?void 0:e.value_type;return"datetime"===i||"date"===i}isLocationField(t){const e=(this.featuredFields||[]).find(e=>e.key===t),i=null==e?void 0:e.value_type;return"state"===i||"district"===i||"ward"===i}locationLeaf(t){const e=t.split(">");return e[e.length-1].trim()}primaryUrn(t){const e=t;if(e.urn)return"string"==typeof e.urn?e.urn:e.urn.display||"";if(Array.isArray(e.urns)&&e.urns.length>0){const t=e.urns[0];return"string"==typeof t?t.split(":")[1]||t:(null==t?void 0:t.display)||(null==t?void 0:t.path)||""}return""}}i([ft({type:String,attribute:"fields-endpoint"})],Dp.prototype,"fieldsEndpoint",void 0),i([ft({type:Boolean})],Dp.prototype,"anon",void 0),i([vt()],Dp.prototype,"featuredFields",void 0);const Mp={text:"Text",numeric:"Number",number:"Number",datetime:"Date & Time",state:"State",ward:"Ward",district:"District"},Pp=t=>Mp[t.value_type]||t.value_type||"",zp=(t,e)=>{if(!e)return!0;return[t.label,t.key,Pp(t)].join(" ").toLowerCase().indexOf(e.toLowerCase())>-1};class Ip extends Vh{constructor(){super(...arguments),this.headerTitle="",this.contentMenuEndpoint="",this.detailEndpoint="",this.otherFieldKeys=[],this.query="",this.searchOpen=!1,this.detailField=null,this.detail=null,this.prepareGhost=t=>{t.style.margin="0",t.style.boxSizing="border-box",t.style.background="var(--surface, #fff)",t.style.border="1px solid var(--border, #e4e7ec)",t.style.borderRadius="var(--curvature, 6px)",t.style.boxShadow="var(--shadow-1, 0 2px 6px rgba(0, 0, 0, 0.12))"},this.handleDetailClosed=()=>{this.detailField=null}}static get styles(){return d`
|
|
10693
10695
|
${Po}
|
|
10694
10696
|
|
|
10695
10697
|
:host {
|
|
@@ -12973,7 +12975,7 @@ background: #ccc;
|
|
|
12973
12975
|
${this.renderUploader()}
|
|
12974
12976
|
</div>
|
|
12975
12977
|
</div>
|
|
12976
|
-
</div>`}}i([ft({type:String,attribute:!1})],Gp.prototype,"endpoint",void 0),i([ft({type:Boolean})],Gp.prototype,"pendingDrop",void 0),i([ft({type:Boolean})],Gp.prototype,"ignoreDrops",void 0),i([ft({type:String})],Gp.prototype,"icon",void 0),i([ft({type:String})],Gp.prototype,"accept",void 0),i([ft({type:Number})],Gp.prototype,"max",void 0),i([ft({type:Array})],Gp.prototype,"attachments",void 0),i([ft({type:Boolean,attribute:!1})],Gp.prototype,"uploading",void 0);let Xp="dev";try{Xp="0.
|
|
12978
|
+
</div>`}}i([ft({type:String,attribute:!1})],Gp.prototype,"endpoint",void 0),i([ft({type:Boolean})],Gp.prototype,"pendingDrop",void 0),i([ft({type:Boolean})],Gp.prototype,"ignoreDrops",void 0),i([ft({type:String})],Gp.prototype,"icon",void 0),i([ft({type:String})],Gp.prototype,"accept",void 0),i([ft({type:Number})],Gp.prototype,"max",void 0),i([ft({type:Array})],Gp.prototype,"attachments",void 0),i([ft({type:Boolean,attribute:!1})],Gp.prototype,"uploading",void 0);let Xp="dev";try{Xp="0.167.0"}catch(t){}const Qp=Xp,Jp=[{type:"has_any_word",name:"has any of the words",operands:1},{type:"has_all_words",name:"has all of the words",operands:1},{type:"has_phrase",name:"has the phrase",operands:1},{type:"has_only_phrase",name:"has only the phrase",operands:1},{type:"has_beginning",name:"starts with",operands:1},{type:"has_text",name:"has some text",operands:0,categoryName:"Has Text"},{type:"has_number",name:"has a number",operands:0,categoryName:"Has Number"},{type:"has_number_between",name:"has a number between",operands:2},{type:"has_number_lt",name:"has a number below",operands:1},{type:"has_number_lte",name:"has a number at or below",operands:1},{type:"has_number_eq",name:"has a number equal to",operands:1},{type:"has_number_gte",name:"has a number at or above",operands:1},{type:"has_number_gt",name:"has a number above",operands:1},{type:"has_date",name:"has a date",operands:0,categoryName:"Has Date"},{type:"has_date_lt",name:"has a date before",operands:1},{type:"has_date_eq",name:"has a date equal to",operands:1},{type:"has_date_gt",name:"has a date after",operands:1},{type:"has_time",name:"has a time",operands:0,categoryName:"Has Time"},{type:"has_phone",name:"has a phone number",operands:0,categoryName:"Has Phone"},{type:"has_email",name:"has an email",operands:0,categoryName:"Has Email"},{type:"has_state",name:"has state",operands:0,categoryName:"Has State",filter:"locations"},{type:"has_district",name:"has district",operands:1,categoryName:"Has District",filter:"locations"},{type:"has_ward",name:"has ward",operands:2,categoryName:"Has Ward",filter:"locations"},{type:"has_group",name:"is in the group",operands:1,visibility:"hidden"},{type:"has_category",name:"has the category",operands:0,visibility:"hidden"},{type:"has_error",name:"has an error",operands:0,categoryName:"Has Error",visibility:"hidden"},{type:"has_value",name:"is not empty",operands:0,categoryName:"Not Empty",visibility:"hidden"},{type:"has_pattern",name:"matches regex",operands:1}],tm=t=>Jp.filter(e=>"hidden"!==e.visibility&&(!e.filter||!!t&&t.includes(e.filter))),em=new Set(["has_beginning","has_number","has_number_between","has_number_lt","has_number_lte","has_number_eq","has_number_gte","has_number_gt","has_pattern"]),im=t=>Jp.find(e=>e.type===t),om=t=>t.map(t=>({value:t.type,name:t.name})),sm={type:"text",required:!1,maxLength:64,placeholder:"(optional)",helpText:"The name to use to reference this result in the flow"},nm={type:"checkbox",label:"Require rules to be localized",helpText:"Each language must specify its own rules for this node"},rm={type:"checkbox",label:"Require categories to be localized",helpText:t=>{var e;const i=null===(e=t.result_name)||void 0===e?void 0:e.trim();if(i){return`Only enable if you plan to use @results.${i.toLowerCase().replace(/\s+/g,"_")}.category_localized`}return"Only enable if you plan to use category_localized in your expressions for this result"},conditions:{visible:t=>!!t.result_name}},am={label:"Save Result",localizable:!1,items:["result_name"],collapsed:t=>!(t._isNew&&t.result_name),getValueCount:t=>!!t.result_name},lm={type:"accordion",multi:!0,sections:[am,{label:"Localization",localizable:!1,items:["localizeRules","localizeCategories"],collapsed:!0,getValueCount:t=>!(!t.localizeRules&&!t.localizeCategories)}]},dm={type:"accordion",multi:!0,sections:[am]},cm={type:"accordion",multi:!0,sections:[am,{label:"Localization",localizable:!1,items:["localizeCategories"],collapsed:!0,getValueCount:t=>!!t.localizeCategories}]};function hm(t,e){var i,o;const s=(null===(i=t.router)||void 0===i?void 0:i.categories)||[],n={};s.forEach(t=>{const i=t.uuid,o=e[i];n[i]={originalName:t.name,localizedName:o&&o.name?Array.isArray(o.name)?o.name[0]||"":o.name:""}});const r=(null===(o=t.router)||void 0===o?void 0:o.cases)||[],a={};return r.forEach(t=>{var i,o;if(!(null===(i=t.arguments)||void 0===i?void 0:i.length)||!t.arguments.some(t=>t))return;const s=e[t.uuid],n=(null===(o=im(t.type))||void 0===o?void 0:o.name)||t.type;a[t.uuid]={operatorName:n,originalArguments:[...t.arguments],localizedArguments:(null==s?void 0:s.arguments)?[...s.arguments]:t.arguments.map(()=>"")}}),{categories:n,rules:a}}function um(t,e){const i={};return t.categories&&Object.keys(t.categories).forEach(e=>{var o,s;const n=t.categories[e],r=(null===(o=n.localizedName)||void 0===o?void 0:o.trim())||"",a=(null===(s=n.originalName)||void 0===s?void 0:s.trim())||"";r&&r!==a&&(i[e]={name:[r]})}),t.rules&&Object.keys(t.rules).forEach(e=>{const o=t.rules[e],s=o.localizedArguments||[],n=o.originalArguments||[],r=s.some((t,e)=>(null==t?void 0:t.trim())&&t.trim()!==(n[e]||""));r&&(i[e]={arguments:s.map(t=>(null==t?void 0:t.trim())||"")})}),i}function pm(t,e,i,o=[]){const s=[],n=[],r=[];return t.forEach(t=>{const a=ae(e,t.name),l=a?i.find(t=>t.uuid===a.exit_uuid):null,d=(null==l?void 0:l.uuid)||Xt(),c=(null==a?void 0:a.uuid)||Xt();if(s.push({uuid:c,name:t.name,exit_uuid:d}),n.push({uuid:d,destination_uuid:(null==l?void 0:l.destination_uuid)||null}),t.case){const e=t.case.arguments[0],i=o.find(t=>{var i;return(null===(i=t.arguments)||void 0===i?void 0:i[0])===e});r.push({uuid:(null==i?void 0:i.uuid)||Xt(),type:t.case.type,arguments:t.case.arguments,category_uuid:c})}}),{categories:s,exits:n,cases:r}}function mm(t,e,i,o,s){const n=s.some(t=>re(t,"Other"))?null:ae(i,"Other"),r=n?o.find(t=>t.uuid===n.exit_uuid):null,a=(null==r?void 0:r.uuid)||Xt(),l=(null==n?void 0:n.uuid)||Xt();return t.push({uuid:l,name:"Other",exit_uuid:a}),e.push({uuid:a,destination_uuid:(null==r?void 0:r.destination_uuid)||null}),l}function gm(t){return e=>{const i={};return t(e,i),{valid:0===Object.keys(i).length,errors:i}}}function fm(t){return t.toLocalizationFormData?t.toLocalizationFormData:"categories"===t.localizable?hm:Array.isArray(t.localizable)?(e=t.localizable,(t,i)=>{const o={uuid:t.uuid};return e.forEach(t=>{const e=i[t];o[t]=Array.isArray(e)&&e[0]||""}),o}):void 0;var e}function vm(t){return t.fromLocalizationFormData?t.fromLocalizationFormData:"categories"===t.localizable?um:Array.isArray(t.localizable)?(e=t.localizable,(t,i)=>{const o={};return e.forEach(e=>{const s=t[e];s&&""!==s.trim()&&s!==i[e]&&(o[e]=[s])}),o}):void 0;var e}const bm="undefined"!=typeof navigator&&/Mac|iPod|iPhone|iPad/.test(navigator.platform);function ym(t){return 0!==t.button||!(!bm||!t.ctrlKey)}function xm(t){if(t.dependency){const e=t.dependency.name||t.dependency.key;return`Cannot find a ${t.dependency.type} for ${e}`}return t.description}function wm(t){const e=20*Math.round(t/20);return Math.max(e,0)}const _m="font-family:SFMono-Regular, Consolas, 'Liberation Mono', Menlo, monospace;font-size:0.95em",km={[Kc.ExpressionPrefix]:`color:${mh.expression};font-weight:600;${_m}`,[Kc.Identifier]:`color:${mh.expression};${_m}`,[Kc.FunctionName]:`color:${mh.fn};font-weight:900;${_m}`,[Kc.StringLiteral]:`color:${mh.string};${_m}`,[Kc.NumberLiteral]:`color:${mh.number};${_m}`,[Kc.Keyword]:`color:${mh.keyword};${_m}`,[Kc.Operator]:`color:${mh.operator};${_m}`,[Kc.ContextRef]:`color:${mh.expression};${_m}`,[Kc.Separator]:`color:${mh.operator};${_m}`,[Kc.Arrow]:`color:${mh.operator};${_m}`,[Kc.Bracket]:`color:${mh.operator};${_m}`,[Kc.Paren]:`color:${mh.paren};${_m}`,[Kc.Whitespace]:_m},Sm=[[/claude|anthropic/i,"anthropic"],[/gpt|openai|o1|o3|o4/i,"openai"],[/gemini|google/i,"gemini"],[/azure|microsoft/i,"azure"],[/deepseek/i,"deepseek"]],Cm=(t,e=!1)=>{const i=th(t||"",e?Fc:Bc),o=[];for(const t of i){const e=!!km[t.type],i=o[o.length-1];i&&i.isExpr===e?i.tokens.push(t):o.push({isExpr:e,tokens:[t]})}const s=t=>{const e=km[t.type];if(!e){const e=t.text.split("\n");return Z`${e.map((t,e)=>Z`${e>0?Z`<br />`:null}${t}`)}`}const i=t.text.split("\n");return Z`${i.map((t,i)=>Z`${i>0?Z`<br />`:null}${t?Z`<span style="${e}">${t}</span>`:null}`)}`};return Z`${o.map(t=>{const e=Z`${t.tokens.map(s)}`;return t.isExpr?Z`<span style="hyphens:none">${e}</span>`:e})}`},$m=(t,e,i=3)=>Z`<div
|
|
12977
12979
|
style="display: -webkit-box; -webkit-line-clamp: ${i}; -webkit-box-orient: vertical; overflow: hidden; word-wrap: break-word; overflow-wrap: break-word; hyphens: auto;"
|
|
12978
12980
|
title="${e}"
|
|
12979
12981
|
>
|