2017-04-21 18 views
2

私は、いくつかの場所で大きな従来の(Vueではなく)システムに組み込む必要があるVueコンポーネントを持っています。 コンポーネントはいくつかのAJAXリクエストを作成し、データベースのレコードIDの配列に基づいて情報を表示します。通常、この情報はページ読み込み時に受け取ります。配列は、サーバによってページテンプレートに直接埋め込まれた、およびコンポーネントに小道具として渡され、そのようなものです:外部状態へのVueコンポーネントデータのバインド

let config = { 
    records: {{ template_code_outputting_array }}, 
    ...otherConfigOptions 
} 

let app = new Vue({ 
    el: '#app', 
    store, 
    render: h => h(ComponentName, { 
    props: config 
    }) 
}) 

私の問題は、画面のいずれかにそれがに埋め込むことが必要であることをデータベースレコードでありますは、ページロード時に事前設定されるのではなく、検索と追加のタイプのAJAXインターフェイスを使用してユーザーが動的に選択できるため、コンポーネントをユーザーの選択と同期させて再描画できるようにする必要があります必要。

私は実用的なソリューションを持っていますが、それは理想から遠いです。

app.$children[0].recordsChanged(newSelection) 

しかし、明らかに、これはありません:私は現在、直接コンポーネントが独自の内部コピーを更新できるように、新しい選択を渡し、コンポーネントにユーザーが自分の選択にいくつかの変更を行うたびにメソッドを呼んでいます反応があり、ハッキリのような気がします。私は、コンポーネントに直接対処するべきではないと感じています。私が呼んでいる機能は、外部使用のためのみです。コンポーネントの中には何も使用しません。

私はデータに結合値を試してみたグローバル変数への(再び理想的ではないですが、私は多くの選択肢を持っていないもの)、その後変化に再レンダリングトリガする時計メソッドを追加します。明らかにスカラー値は、値ではなく参照では機能しませんが、オブジェクトでラップするとどちらも機能しないように見えます。彼らは正常にバインドし、初期値を提供しますが、オブジェクトを更新する(値を直接変更するか、オブジェクトを新しいオブジェクトに置き換える)、メソッドまたは任意の反応をトリガしていないようです。

これを実行するためのベストプラクティスはありますか、現在の私のアプローチは、私が望むことができる最高のものですか?

+1

は、なぜあなたはVUEイベントバスを使用して文句を言いませんか? 'var bus = new Vue({}) 'のように。 $ emit( "someEvent"、{new:data}) 'あなたのコンポーネントでは' bus on $ on(someEvent "、doSomething)'を実行することができます。バス変数をウィンドウに割り当ててください。 – AfikDeri

+0

@Afik​​Deri実際に多くの助けになりましたので、ありがとうございます。私はemitをラップする関数をエクスポートすることができたので、外部コードを変更する人は誰もVueの知識を必要としません。私はそれを完全に反応させ、関数呼び出しを完全に避けることができればそれでもなおいいですが、私はそれを行うよりクリーンな方法はないと考え始めています。 –

答えて

1

イベントバス(コメントの中でAfikDeriが提案する)は良い解決策です。それは簡単なインターフェイスを提供します。

データを有効にすることも可能です(with some caveats)。 オブジェクトは、データ項目を初期化するために使用され、それ自体がリアクティブになります。あなたの配列do so in the approved waysを変更するものなら、あなたのVue内の変更を見るべきです。

let stuff = [2, 3, 5]; 
 

 
const v = new Vue({ 
 
    el: '#app', 
 
    data: { 
 
    reactiveStuff: stuff 
 
    }, 
 
    components: { 
 
    myComponent: { 
 
     props: ['arr'], 
 
     template: '<div><div v-for="item in arr">{{item}}</div></div>' 
 
    } 
 
    } 
 
}); 
 

 
setTimeout(() => { 
 
    stuff.push(7); 
 
}, 1200);
<script src="//cdnjs.cloudflare.com/ajax/libs/vue/2.2.6/vue.min.js"></script> 
 
<my-component id="app" :arr="reactiveStuff"> 
 
</my-component>

関連する問題