Dapr 入門チュートリアル: 公開と購読

Dapr 入門チュートリアル: 公開と購読

先ほど、Dapr でサービス呼び出しを行う方法と、最も単純な状態管理について学習しました。このセクションでは、Dapr のパブリッシュ/サブスクライブ モードを有効にする方法を学習します。パブリッシャーは特定のトピックに関するメッセージを生成し、サブスクライバーは特定のトピックに関する情報をリッスンします。

  • 公開サービスを使用すると、開発者はトピックにメッセージを繰り返し公開できます。
  • Pub/sub コンポーネントはこれらのメッセージを処理のためにキューに入れます。
  • トピック サブスクライバーはキューからメッセージを取得して処理します。

次に使用する例には、パブリッシャーが含まれています。

  • React フロントエンド メッセージ ジェネレーター

さらに 3 人のメッセージ サブスクライバーが含まれます:

  • Node.js サブスクライバー
  • Python 購読者
  • C# サブスクライバー

Dapr は、プラグ可能なメッセージ バスを使用してパブリッシュ/サブスクライブをサポートし、接続されたサービスの相互運用性を向上させるために、共通のイベント エンベロープ形式として CloudEvents (CNCF プロジェクト) にメッセージを配信します。

ここでは Redis Streams (Redis バージョン = > 5 で有効化) を使用しますが、RabbitMQ や Kafka などのミドルウェアを使用することもできます。次の図は、ローカル モードでコンポーネントが相互に接続される様子を示しています。

dapr パブリッシュ/サブスクライブ

ローカル初期化

Dapr を使用すると、ローカル マシンからクラウド環境に同じマイクロサービスをデプロイできます。この利便性を説明するために、まずこのサンプル プロジェクトをローカルにデプロイし、次に Kubernetes 環境にデプロイします。

Dapr サービスをローカルで使用するには、まず Dapr をローカルで初期化する必要があります。

 $ dapr 初期化

何らかのネットワーク上の理由により、上記のコマンドが正常に初期化されない可能性があります。オフラインインストールを使用できます。 https://github.com/dapr/installer-bundle/releases にアクセスして、対応するシステムの Bundle 👝 パッケージをダウンロードし、解凍します。たとえば、ここに Mac M1 がある場合、ダウンロードするには次のコマンドを使用します。

 $ wget https://github.91chi.fun/https://github.com/dapr/installer-bundle/releases/download/v1.8.4/daprbundle_darwin_arm64.tar.gz
$ tar - xvf daprbundle_darwin_arm64タール日本語
x daprbundle /
x daprbundle / README.md
x daprバンドル/ dapr
x daprbundle / details.json
x daprbundle / 配布/
x daprbundle / dist / daprd_darwin_arm64タール日本語
x daprbundle / dist / dashboard_darwin_arm64 .tar .gz
x daprbundle / dist / placement_darwin_arm64タール日本語
x daprbundle / docker /
x daprbundle / docker / daprio - dapr - 1.8.4.tar.gz

その後、次のコマンドを使用して再初期化できます。

 $ dapr init -- from - dir daprbundle /
ハイパースペースジャンプ...
--from - dir フラグを使用したローカルバンドルのインストールは現在プレビュー機能あり 変更される可能ありますCLI バージョン1.7 以降のみ使用できます
ℹ️ ランタイムバージョン1.8.4 インストール
バイナリを抽出してコンポーネント設定しています...
Dapr ランタイム/ Users / cnych / インストールされましたdapr / bin の場合、 daprd 直接実行したい場合 のコマンド実行してパス追加できます
エクスポートPATH = $ PATH : /Users/cnych/.dapr/bin
8 d7366c22fd8 : レイヤーをロード中[ ==============================================================> ] 3.697 MB / 3.697 MB
61f 7f 94319f 6 : レイヤーをロード中[ =============================================================> ] 238.6 MB / 238.6 MB
バイナリ抽出してコンポーネント設定しています... 読み込まれたイメージ: daprio / dapr : 1.8.4
バイナリを抽出し コンポーネント設定しています...
バイナリを抽出し コンポーネントのセットアップ完了しました
ℹ️ daprd バイナリ/ Users / cnych / インストールましたdapr / bin
ℹ️ dapr_placement コンテナが実行中です
ℹ️ 実行中のコンテナを確認するには、 `docker ps` を使用します
$ dapr バージョン
CLI バージョン: 1.8.0
ランタイムバージョン: 1.8.4

デフォルトでは、 ​zipkin​トレース サービスは有効になっています。上記のコマンドを使用して初期化します。対応するコンテナがない場合は、 ​docker run --name dapr_zipkin -d -p 9411:9411 dockerproxy.com/openzipkin/zipkin​​​ を使用してサービスを開始できます。 Redis サービスも実行する必要があります: ​docker run --name dapr_redis -d -p 6379:6379 dockerproxy.com/redislabs/rejson​

dapr コンテナ

ニュース購読サービス

ここでは、以前に使用したクイックスタート プロジェクトを引き続き使用し、プロジェクトをローカルに複製します。

 gitクローン [-b <dapr_version_tag>] https://github.com/dapr/quickstarts.git

tutorials/pub_sub ディレクトリに移動します。

 ➜ パブリッシュサブスクライブgit :(622b7d9) ls
README.md デプロイ makefile message_b.json node-subscriber react-form
csharp-subscriber img message_a.json message_c.json python-subscriber

Nodeメッセージサブスクリプションサービスを実行する

まず、Dapr を使用してノード メッセージ サブスクリプション サービスを実行します。 node-subscriber ディレクトリに移動し、依存関係をインストールします。

 $ cdノードサブスクライバー
$ npm install # または yarn

ノード メッセージ サブスクリプション サービスを実行するには、次のコマンドを実行します。

 $ dapr実行--app -idノード サブスクライバー--app -port 3000 ノードapp.js
ℹ️ ID node-subscriber で Dapr を起動しています。 HTTP ポート: 50728 。 gRPC ポート: 50729
INFO[0000] Dapr Runtime を起動中--バージョン1 .8.4 --コミット 18575823c74318c811d6cd6f57ffac76d5debe93 app_id = node-subscriber インスタンス= MBP2022.local スコープ= dapr.runtime タイプ= log ver = 1 .8.4
# ......
INFO[0000] アプリは次のトピックにサブスクライブされています: [AB] pubsub = pubsub app_id = node-subscriber instance = MBP2022.local scope = dapr.runtime type = log ver = 1 .8.4 経由
INFO[0000] daprが初期化されました。ステータス: 実行中。初期化経過時間312 .69599999999997 ミリ秒app_id = node-subscriber インスタンス= MBP2022.local スコープ= dapr.runtime タイプ= log バージョン= 1 .8.4
INFO[0000] 配置テーブルが更新されました。バージョン: 0 app_id = node-subscriber インスタンス= MBP2022.local スコープ= dapr.runtime.actor.internal.placement タイプ= log バージョン= 1 .8.4
ℹ️ アプリメタデータを更新するコマンド: node app.js
起動して実行中です! Dapr とアプリのログの両方がここに表示されます。

上記のコマンドでは、app-id はマイクロサービスの一意の識別子、--app-port は Node アプリケーションが実行されているポート、最後にアプリケーションを実行するコマンドは node app.js です。

Python メッセージサブスクリプションサービスの実行

次に、Dapr を使用して Python メッセージ サブスクリプション サービスを実行します。 python-subscriber ディレクトリに移動します。

 $ cd python - サブスクライバー

アプリケーションの依存関係をインストールします。

 $ pip3 インストール-r 要件.txt 

ここでも、dapr run を使用してサブスクリプション サービスを実行します。

 $ dapr run --app - id python - subscriber --app - port 5001 python3 app .py  
ℹ️ ID python - subscriber Dapr を起動しますHTTP ポート: 55508。gRPC ポート: 55509
INFO [ 0000 ] Dapr ランタイム開始しています-- バージョン1.8.4 -- コミット18575823 c74318c811d6cd6f57ffac76d5debe93 app_id = python - subscriber instance = MBP2022ローカルスコープ= daprランタイムタイプ= ログバージョン= 1.8.4
INFO [ 0000 ] ログレベル次のように設定されました: info app_id = python - subscriber instance = MBP2022ローカルスコープ= daprランタイムタイプ= ログバージョン= 1.8.4
INFO [ 0000 ] gRPC メトリクスミドルウェアが有効になりました。app_id = python - subscriber instance = MBP2022ローカルスコープ= daprランタイムgrpc内部タイプ= ログバージョン= 1.8.4
INFO [ 0000 ] 内部gRPC サーバーポート55514 実行されています。app_id = python - subscriber instance = MBP2022ローカルスコープ= daprランタイムタイプ= ログバージョン= 1.8.4
INFO [ 0000 ] アプリケーションプロトコル: httpポート5001 待機していますアプリそのポートリッスンするまでブロックますapp_id = python - サブスクライバーインスタンス= MBP2022ローカルスコープ= daprランタイムタイプ= ログバージョン= 1.8.4
INFO [ 0000 ] ポート5001 アプリケーションが検出されました。app_id = python - subscriber instance = MBP2022ローカルスコープ= daprランタイムタイプ= ログバージョン= 1.8.4
警告[ 0000 ] [ 非推奨の通知] 受信サービス呼び出し要求デフォルトのコンテンツタイプ追加することは非推奨であり 将来削除される予定です詳細については、 https://docs.dapr.io/operations/support/support-preview-features/ を参照してください構成オプション `ServiceInvocation.NoDefaultContentType` を true に設定することで、今すぐ新しい動作を選択できます。 app_id=python-subscriber インスタンス=MBP2022.local スコープ=dapr.runtime タイプ=ログ バージョン=1.8.4
== APP == * Flask アプリ「app」 の提供( 遅延読み込み)
== APP == * 環境: 本番
== APP == 警告: これは開発サーバーです 稼働環境では使用しないください
== APP == 代わりに本番環境のWSGI サーバー使用してください
== APP == * デバッグモード: オフ
== APP == * http 実行中: //127.0.0.1:5001/ (終了するには CTRL+C を押してください)
ℹ️ アプリコマンドメタデータを更新しています: python3 app .py
起動して実行中です! Dapr とアプリのログの両方がここに表示されます。

ここでは C# 環境がないため、Node および Python メッセージ サブスクリプション サービスのみを実行します。

メッセージ公開サービス

次に、フロントエンドのメッセージ公開サービスである React を実行してみましょう。再度、 react-form プロジェクト ディレクトリに移動します。

 $ cd react - フォーム

次に、次のコマンドを実行して依存関係をインストールし、サービスをビルドします。

 $ npm ビルドクライアントを実行
$ npm インストール

ビルドが完了したら、次の dapr コマンドを使用してフロントエンド サービスを開始できます。

 $ dapr run --app - id react -form --app - port 8080 npm run start 実行します
ℹ️ ID react - form Dapr を開始しますHTTP ポート: 57303。gRPC ポート: 57304
INFO [ 0000 ] Dapr ランタイム開始しています- バージョン1.8.4 - コミット18575823 c74318c811d6cd6f57ffac76d5debe93 app_id = react -form instance = MBP2022 ローカルスコープ= daprランタイムタイプ= ログバージョン= 1.8.4
# ......
== アプリ==
== APP == > react - フォーム@1 .0 .0 開始
== APP == > ノードサーバーjs
== アプリ==
== APP == ポート8080 リッスンしています
INFO [ 0000 ] ポート8080 アプリケーションが検出されました。app_id = react - form instance = MBP2022ローカルスコープ= daprランタイムタイプ= ログバージョン= 1.8.4
# ......
INFO [ 0000 ] dapr が初期化されましたステータス: 実行中初期経過時間760.39 ミリ秒app_id = react -form インスタンス= MBP2022ローカルスコープ= daprランタイムタイプ= ログバージョン= 1.8.4
ℹ️ アプリコマンドメタデータの更新: npm run start
起動して実行中です! Dapr とアプリのログの両方がここに表示されます。

INFO [ 0001 ] 配置テーブルが更新されましたバージョン: 0 app_id = react - form instance = MBP2022ローカルスコープ= daprランタイム俳優内部配置タイプ= ログバージョン= 1.8.4

== APP == Listening on port 8080! のようなログが表示されたら、アプリケーションが正常に起動したことを意味します。次に、ブラウザで http://localhost:8080 にアクセスして、フロントエンド アプリケーションにアクセスします。

フロントエンドページ

たとえば、メッセージ タイプ A を選択し、メッセージ コンテンツを入力して、[送信] をクリックして送信し、上記の 2 つのメッセージ サブスクライバー サービス (Node と Python) のログを確認します。

件名を選択し、テキストを入力してメッセージを送信してください。それぞれの Dapr ログを監視します。

Dapr メッセージ購読および公開サービス

Node サブスクライバーはタイプ A と B のメッセージを受信し、Python サブスクライバーはタイプ A と C のメッセージを受信するので、各コンソール ウィンドウのログ表示に注意してください。

さらに、Dapr CLI はテスト用のメッセージを公開するメカニズムを提供します。たとえば、次のコマンドを使用してメッセージを公開できます。

 $ dapr publish -- publish - app - id react - form -- pubsub pubsub -- topic A -- データファイルmessage_a .json  

dapr-cli 公開

この時点で、メッセージのサブスクリプションと公開に Dapr を使用する機能のデモンストレーションが完了しました。

Kubernetesで実行

上記では、デモ サービスをローカルに展開しました。 Dapr を使用して開発されたサービスはプラットフォームから独立しており、クラウド環境に簡単に移行できることがわかっています。たとえば、上記のサンプル アプリケーションを Kubernetes クラスターにデプロイします。

Kubernetes で同じコードを実行するには、まず Redis ストレージをセットアップし、次にマイクロサービスをデプロイする必要があります。同じマイクロサービスが使用されますが、最終的なアーキテクチャは異なります。

K8sで実行

Helm を使用して、bitnami の下に redis アプリケーションをインストールしました。

 $ helm リポジトリbitnami を追加しますhttps://charts.bitnami.com/bitnami
$ helm リポジトリの更新
$ helm インストールredis bitnami / redis

Redis サービスを取得したら、パブリッシュ/サブスクライブ コンポーネントを作成する必要があります。前回の記事では、Redis を使用する状態管理コンポーネントを作成しました。対応するコンポーネント リソース リストは次のとおりです。

 # デプロイ/ redisヤム
apiバージョン: dapr .io / v1alpha1
種類: コンポーネント
メタデータ:
名前: pubsub
仕様:
タイプ: pubsubレディス
バージョン: v1
メタデータ:
# これらの設定は `helm install を使用するすぐ機能ます
# bitnami / redis `独自設定がある場合
# `redis - master : 6379 ` 自分のRedis マスターアドレス置き換え
# 独自Secret の名前を使用したRedis パスワード詳細については、
# https://docs.dapr.io/operations/components/component-secrets を参照してください
- 名前: redisHost
: redis - マスター: 6379
- 名前: redisPassword
シークレットキーリファレンス:
名前: レディス
キー: redis - パスワード
認証:
シークレットストア: kubernetes

上記のリソース リストを適用するだけです。

 $ kubectl apply -f デプロイ/ redis .yaml
成分ダップルio / pubsub が作成されました
$ kubectl コンポーネントを取得する
名前年齢
pubsub 26
ステートストア45h

これで、Redis をミドルウェアとして使用するパブリッシュ/サブスクライブ コンポーネントができました。上記のオブジェクトの型は​pubsub.redis​​ ​であることに注意してください。

レディスパブリッシュサブスクライブ

次に、Python、Node、React-form の 3 つのマイクロサービスをデプロイします。

 $ kubectl apply -f deploy / node - サブスクライバー.yaml
$ kubectl apply -f deploy / python -subscriber .yaml
$ kubectl apply -f デプロイ/ react -form .yaml

デプロイ後、ポッドのステータスを確認します。

 $ kubectl ポッドを取得する
名前準備完了ステータス再起動年齢
ノード- 加入者- 5 b5777c785 - z8jzn 2 / 2 実行中0 30 m
python - 加入者- 76 d9fc6c87 - ffj7r 2 / 2 実行中0 30 m
反応- フォーム- 68 db4b7777-7 qmtj 2 / 2 実行中0 30 m

react-form マイクロサービスは、LoadBalancer タイプのサービスを通じてサービスを外部に公開します。

 $ kubectl svc を取得します
名前タイプクラスタ- IP 外部- IP ポート( S ) 年齢
ノード- サブスクライバー- dapr ClusterIP なし< なし> 80 / TCP50001 / TCP50002 / TCP9090 / TCP 31
python - subscriber - dapr ClusterIP なし< なし> 80 / TCP50001 / TCP50002 / TCP9090 / TCP 31
反応- フォームLoadBalancer 10.110 .199 .146 192.168 .0 .51 80 : 32510 / TCP 30 m
react - form - dapr ClusterIP なし< なし> 80 / TCP50001 / TCP50002 / TCP9090 / TCP 30

その後、割り当てられた EXTERNAL-IP を介してフロントエンド サービスにアクセスできるようになります。同様に、フロントエンド ページでいくつかの異なるメッセージ通知を送信し、kubectl logs を使用して Node および Python サブスクリプション サービスのログを観察します。

 $ kubectl logs -- セレクターapp = node - subscriber - c node - subscriber
$ kubectl logs -- セレクターapp = python - subscriber - c python - subscriber

K8s での Pub-Sub

仕組み

サンプルのパブリッシュ/サブスクライブ アプリケーションがローカルと Kubernetes で実行されたので、これがどのように動作するかを分析してみましょう。アプリケーションは 2 つのサブスクライバーと 1 つのパブリッシャーに分かれています。

ノードメッセージサブスクリプションサービス

node-scriber ディレクトリに戻り、Node.js サブスクライバー コード app.js を確認します。このサービスは、Express を通じて 3 つの API エンドポイントを公開します。 1 つ目は GET エンドポイントです。

 アプリ取得( "/dapr/subscribe" 、 ( _reqres ) => {
解像度json ([
{
pubsub名: "pubsub"
トピック: 「A」
ルート「A」
},
{
pubsub名: "pubsub"
トピック: 「B」
ルート「B」
},
]);
});

このコードは、pubsub コンポーネントにサブスクライブするトピックを Dapr に指示します。 ​route​ 、メッセージを処理するためにルーティングするエンドポイントを示します。デプロイされると (ローカルまたは Kubernetes 内)、Dapr はサービスを呼び出して、何かにサブスクライブされているかどうかを判断します。他の 2 つのエンドポイントはバック エンドポイントです。

 アプリpost ( "/A" 、 ( 要求応答) => {
コンソールlog ( "A: " , 要求. 本文. データ. メッセージ);
解像度送信ステータス( 200 );
});

アプリpost ( "/B" 、 ( 要求応答) => {
コンソールlog ( "B: " , 要求. 本文. データ. メッセージ);
解像度送信ステータス( 200 );
});

これら 2 つのエンドポイントは、各トピック タイプからのメッセージを処理します。ここではメッセージをログに記録するだけですが、より複雑なアプリケーションでは、ここでビジネス ロジックを処理する必要があります。

さらに、Subscription オブジェクトを直接作成して、どのサービスのどのコンポーネントのどのトピックをサブスクライブするかを宣言することもできます。

Python メッセージサブスクリプションサービス

また、python-subscriber ディレクトリに移動し、Python サブスクリプション サービスのコード ファイル app.py を表示します。 Node.js サブスクライバーと同様に、3 つの API エンドポイントを公開しますが、ここでは flask を使用し、最初のエンドポイントは GET エンドポイントです。

 @アプリルート( '/dapr/subscribe'メソッド= [ 'GET' ])
デフサブスクライブ():
サブスクリプション= [{
'pubsubname' : 'pubsub''topic' : 'A''route' : 'A'
}, {
'pubsubname' : 'pubsub''topic' : 'C''route' : 'C'
}]
jsonify ( サブスクリプション) を返す

同様に、これは Dapr に pubsub コンポーネントのどのトピックをサブスクライブするかを指示します。ここでは、トピック A と C を持つ pubsub というコンポーネントをサブスクライブします。これらのトピックのメッセージは、他の 2 つのルートによって処理されます。

 @アプリルート( '/A'メソッド= [ 'POST' ])
a_subscriber () を定義します:
print ( f 'A: {request.json}'flush = True )
print ( 'トピック "{}" のメッセージ "{}" を受信しました' . format ( request . json [ 'data' ][ 'message' ], request . json [ 'topic' ]), flush = True )
json を返しますダンプ({ 'success' : True }), 200 , { 'ContentType' : 'application/json' }

@アプリルート( '/C'メソッド= [ 'POST' ])
c_subscriber () を定義します:
print ( f 'C: {request.json}'flush = True )
print ( 'トピック "{}" のメッセージ "{}" を受信しました' . format ( request . json [ 'data' ][ 'message' ], request . json [ 'topic' ]), flush = True )
json を返しますダンプ({ 'success' : True }), 200 , { 'ContentType' : 'application/json' }

Reactフロントエンドアプリケーション

上記は2つのサブスクリプションサービスです。次に出版社を見てみましょう。当社のパブリッシャーはクライアントとサーバーに分かれています。

クライアントは、Create React App を使用して開始されたシンプルなシングルページ React アプリケーションです。関連するクライアント コードは react-form/client/src/MessageForm.js にあります。ユーザーがフォームを送信すると、React の状態は最新の集約された JSON データで更新されます。デフォルトでは、データは次のように設定されます。

 {
メッセージタイプ: "A"
メッセージ""
};

フォームが送信されると、集約された JSON データがサーバーに送信されます。

 フェッチ( "/publish" 、 {
ヘッダー: {
受け入れる: "application/json"
「コンテンツタイプ」 : 「application/json」
},
メソッド: "POST"
本文: JSON文字列化( this . state )、
});

サーバーは、POST エンドポイント /publish を公開する典型的な Express アプリケーションです。これはクライアントからのリクエストを受け取り、Dapr に従って公開します。 Express の組み込み JSON ミドルウェア関数は、受信リクエスト内の JSON を解析するために使用されます。

 アプリexpress.json () 使用します

このようにして、送信された messageType を取得し、メッセージを公開するために使用するトピックを決定できます。 Dapr を使用してメッセージを公開するには、Dapr が提供する API エンドポイント (http://localhost:<DAPR_URL>/publish/<PUBSUB_NAME>/<TOPIC>) を直接使用することもできます。取得したデータに基づいて Dapr メッセージ公開用の URL を構築し、JSON データを送信します。 POST リクエストは、正常に完了した後、応答で成功コードを返す必要もあります。

 const publishUrl = `$ { daprUrl } / publish / $ { pubsubName } / $ { req . メッセージタイプ} ` ;
axios を待ちますpost ( publishUrlreqbody );
res を返します送信ステータス( 200 );

daprUrl アドレスのポートは、次のコードを使用して取得できます。

 const daprUrl = `http : //localhost:${process.env.DAPR_HTTP_PORT || 3500}/v1.0`;

デフォルトでは、Dapr は 3500 で実行されますが、Dapr をローカルで実行し、別のポートに設定すると (CLI 実行コマンドで --app-port フラグを使用)、そのポートは環境変数としてアプリケーションに挿入されます。

サーバーは、デフォルトのホームページ/ルートのリクエストをビルドされたクライアント側コードに転送することで、React アプリケーション自体もホストします。

 アプリ取得( "/"関数( _reqres ) {
解像度sendFile ( path . join ( __dirname , "client/build" , "index.html" ));
});

そのため、サーバーを介してフロントエンドページに直接アクセスできます。

パブリッシュ/サブスクライブ モデルは、マイクロサービス開発において非常に重要なモデルであり、高いスケーラビリティと疎結合を実現するために使用できます。パブリッシュとサブスクライブは、高いスケーラビリティを必要とする大規模なアプリケーションでよく使用されます。パブリッシュおよびサブスクライブ アプリケーションは、通常、従来のクライアント/サーバー アプリケーションよりもスケーラビリティが優れています。 Pub-sub を使用すると、コンポーネントを完全に分離できるため、パブリッシャーはサブスクライバーについて知る必要がなくなり、サブスクライバーもパブリッシャーについて知る必要がなくなります。これにより、開発者は相互に直接依存しない、よりスリムなマイクロサービスを作成できます。

上記の例から、開発に Dapr のパブリッシュ/サブスクライブ モデルを使用すると、完全に​localhost​プログラミングになることがわかります。

<<:  SaaS プロバイダーを選択する際に尋ねるべき重要な質問

>>:  外部データ製品の構築がなぜ難しいのでしょうか?

推薦する

2022 年のクラウド仮想化の 5 つのトレンド

サーバー仮想化は、VMware が登場した約 20 年前に爆発的に普及しました。しかし、長い道のりを...

クラウドコンピューティングがIT部門だけの責任ではない理由

過去 1 年間、企業はオフィスでの勤務から自宅からのリモート勤務への移行を可能にするテクノロジーを導...

仲人から家政婦へ:Dunhuang.com B2Bの自己償還

ホウ・ジヨンJoyo.com の創設者から DHgate.com の現 CEO に至るまで、Wang...

ByteDanceはビッグVのLi Ziqiに数千万ドルを賭けている。その目的は何でしょうか?

Liziqiは幸運な人だと言う人が多すぎます。実際、李子奇の現在の状況は、最初から最も適切な道を選ん...

盛業:人間本位を堅持し、産業技術の配置を加速する

疫病の影響、貿易環境の変化、戦争紛争の影響…全体的な経済低迷とマクロ経済環境への高圧力の状況下で、す...

racknerd: DC5 データセンター VPS、60Gbps 防御、3 つのネットワークの完全最適化の簡単なレビュー!

Racknerd は昨日、Sharktech のロサンゼルス データ センターの VPS サービスに...

分散型グローバル一意 ID スキームはそんなにたくさんあるのでしょうか?

[[403814]]この記事はWeChatの公開アカウント「Java Geek Technology...

gcorelabs: ロシア極東データセンター - 「ブラゴヴェシチェンスク」、月額 1.08 ユーロの VPS の簡単なレビュー、モバイルをやめるアドバイス!

gcorelabs 極東データセンター ウラジオストクはホスト キャットでテストされ、リリースされま...

メーデー後の新たな始まり

メーデー後の新たな始まり - ウェブサイトをランク付けするには?この間、私のサイトの多くはランキング...

namecheap: 移管ドメイン名が 30% オフ、1 週間有効、更新として考えてもお得です!

本日より、Namecheap はドメイン名移管の 1 週間限定プロモーションを開始しました。直接 3...

検索ボックス: デザイナーが注意すべき 5 つの詳細

編集者注: ユーザー インターフェイスの設計は、ユーザーを維持したいアプリケーションや Web サイ...

PPCは大きな罠

インターネットは巨大であり、多くの企業は、顧客が検索エンジンを通じて自社を見つけられるようにするため...

hosthatch - $32/年/512MB メモリ/20GB SSD/1TB トラフィック/G ポート/3 つのデータセンター

Hosthatch はフロリダ州タンパに登録されています。Facebook でハードウェア機器を公開...

WeChat パブリック アカウントのプロモーションに関するヒントをご紹介します。ポジショニングやコンテンツについて語る大物たちの話はもう聞かないでください。

みなさんは公式アカウントに興味があるようですが、それらの記事だけでは不十分なので、今日はもうできない...