ホーム 記事一覧 ブック DH週間トピックス 検索 このサイトについて
RSS English
VueUseを用いたテキスト選択(Nuxt3)

VueUseを用いたテキスト選択(Nuxt3)

概要 Nuxt3(Vue3)を用いたテキストの選択機能の実装にあたり、VueUseを使用してみましたので、その備忘録です。 https://vueuse.org/ デモ 以下のページからお試しいただけます。 https://nuxt3-demo-git-main-nakamura196.vercel.app/textSelection ソースコードは以下です。 https://github.com/nakamura196/nuxt3-demo/blob/main/pages/textSelection.vue インストール方法 以下のページに記載があります。 https://vueuse.org/guide/ 具体的な手順は、以下のとおりです。 npm i -D @vueuse/nuxt @vueuse/core // nuxt.config.ts export default defineNuxtConfig({ modules: [ '@vueuse/nuxt', ], }) まとめ テキスト選択以外にも、便利な機能が色々と使えるようなので、引き続き試してみたいと思います。

Next.js for DrupalにおけるDrupal Search APIを用いた検索(ファセット検索など)

Next.js for DrupalにおけるDrupal Search APIを用いた検索(ファセット検索など)

概要 Next.js for Drupalを試してみました。 https://next-drupal.org/ 以下の「Get Started」の通りにすすめることで、Next.jsとDrupalを連携させることができました。 https://next-drupal.org/learn/quick-start また、以下の記事で、ファセット検索の実装例が紹介されています。 https://next-drupal.org/guides/search-api 本記事では、特に後者のファセット検索の実現に関する備忘録です。 Search API 以下、Serverとindexを作成します。 公式サイトでは以下が参考になります。 https://www.drupal.org/docs/contributed-modules/search-api 日本語サイトでは以下が参考になります。 https://www.acquia.com/jp/blog/introduction-to-search-api-1 Serverの作成 indexの作成 今回、test_index_20230417というインデックスを作成します。 さらに、タイトルをフィールドとして追加しました。 その後、インデクシングを行います。 JSON:API 上記を行ったところで、キャッシュをクリアします。 /admin/config/development/performance その後、以下のURLからエンドポイントにアクセスできるようになります。 /jsonapi/index/test_index_20230417 以下のようなクエリパラメータによって、検索結果の絞り込みができます。 /jsonapi/index/test_index_20230417?filter[title]=更新したタイトル { "jsonapi": { "version": "1.0", "meta": { "links": { "self": { "href": "http://jsonapi.org/format/1.0/" } } } }, "data": [ { "type": "node--service", "id": "82a34c35-f1b7-49eb-81ac-f15d0deac22c", "links": { "self": { "href": "https://xxx/jsonapi/node/service/82a34c35-f1b7-49eb-81ac-f15d0deac22c?resourceVersion=id%3A5075" } }, "attributes": { "drupal_internal__nid": 4, "drupal_internal__vid": 5075, "langcode": "en", "revision_timestamp": "2023-04-12T08:19:00+00:00", "revision_log": null, "status": true, "title": "更新したタイトル", "created": "2023-04-11T02:09:35+00:00", "changed": "2023-04-12T08:19:00+00:00", "promote": false, "sticky": false, "default_langcode": true, "revision_translation_affected": true, ... Facets 以下にアクセスします。 ...

Contentfulの全文検索は2文字以上の検索語が必要?

Contentfulの全文検索は2文字以上の検索語が必要?

Contentfulを使用していますが、2文字以上の検索語が必要そうでした。 A query will ignore search tokens with less than 2 characters. https://www.contentful.com/developers/docs/references/content-delivery-api/#/reference/search-parameters/full-text-search-on-a-field この点は日本語などを含むデータに対して注意が必要そうです。 追記 microCMSでは、1文字からの検索が可能でした。 https://microcms.io/

Drupalのコンテンツの一括削除の方法

Drupalのコンテンツの一括削除の方法

概要 Drupalのコンテンツの一括削除の方法を調べたので、その備忘録です。以下の記事が参考になりました。 https://www.webwash.net/how-to-bulk-delete-content-in-drupal/ 以下の3つの方法が紹介されていました。 Drupal コア UI の使用 (Using Drupal Core UI) Drush の使用 (Using Drush) ビューの一括操作 (VBO) の使用 (Using Drupal Views Bulk Operations (VBO)) Drupal コア UI の使用 以下、日本語訳です。 小さな Drupal サイトがあり、削除するノードが約 300 未満の場合は、この方法を使用する必要があります。これは、Drupal コアの UI を使用すると、デフォルトで一度に 50 ノードしか削除できないためです。サイトが大きくなると、これは面倒になります。 Drush の使用 以下、日本語訳です。 コマンド ラインを使用すると、Drush を使用できます。これが推奨される方法です。 例えば以下では、記事コンテンツ タイプのすべてのノードを削除します。 drush entity:delete node --bundle=article ただ、上記のサイトにも記載がありましたが、PHP メモリ制限にひっかかることがあるようです。Amazon Lightsail上に立てた512MBメモリの環境において、5,000件のコンテンツの一括削除を試みたところ、以下のように制限に引っかかってしまいました。ただし、再度同じコマンドを実行することで、無事に一括削除ができました。 drush entity:delete node --bundle=article 2550/5057 [▓▓▓▓▓▓▓▓▓▓▓▓▓▓░░░░░░░░░░░░░░] 50% PHP Fatal error: Allowed memory size of 268435456 bytes exhausted (tried to allocate 20480 bytes) in /opt/bitnami/drupal/core/lib/Drupal/Core/TypedData/Plugin/DataType/ItemList.php on line 76 PHP Fatal error: Allowed memory size of 268435456 bytes exhausted (tried to allocate 32768 bytes) in /opt/bitnami/drupal/vendor/symfony/http-foundation/Response.php on line 895 specify the chunk/batch size デフォルトでは50件ずつ処理されますが、–chunks=100のように引数を加えることで、バッチサイズを変更できました。 ...

DrupalとAmazon OpenSearch Serviceを接続する

DrupalとAmazon OpenSearch Serviceを接続する

概要 DrupalとAmazon OpenSearch Serviceを接続する機会がありましたので、その備忘録です。以下の記事が参考になりました。 https://www.acquia.com/jp/blog/intergration-with-drupal-and-elasticsearch モジュールのインストール drupal/search_apiとdrupal/elasticsearch_connectorに加えて、nodespark/des-connectorをインストールする必要がありました。 (バージョンの指定方法など、改善の余地があるかもしれません。) composer require "nodespark/des-connector:^7.x-dev" composer require 'drupal/search_api:^1.29' composer require "drupal/elasticsearch_connector ^7.0@alpha" 続けて、以下で有効化します。 drush pm:enable search_api elasticsearch_connector DrupalをElasticsearchに接続する クラスタ 以下にアクセス /admin/config/search/elasticsearch-connector 「Add cluster」をクリックします。 そして、以下のように値を入力します。Amazon OpenSearch ServiceでBasic認証をかけている方法を前提としています。注意点として、「Server URL」に入力する値の末尾に、:443が必要でした。 Elasticsearchサーバーへの接続が成功すると、Cluster Statusに yellow や green と表示されます。 インデックス 次に、任意の作業ですが、インデックスを作成します。「Add index」ボタンを押して、nameだけ入力してみます。結果、以下のようにインデックスが作成されました。 Search APIの設定 今度は、Search API側の設定を行います。以下にアクセスします。 /admin/config/search/search-api サーバの追加 「Add Server」ボタンを押します。特に、BackendにElasticsearchを選択して、Clusterに先程作成したクラスタを選択します。 インデックスの追加 以下の画面には出ていませんが、「Datasources」のところで、「Content」を選択しています。また「Server」で、上記で作成したサーバを選択しています。 次に、末尾の「Save and add fields」ボタンをクリックします。 フィールドの追加 今回は最低限のフィールドとして、Titleを追加しておきます。 追加したフィールドに対するFulltext検索を可能とするために、「Type」を変更します。これらの設定は適宜変更してください。 再インデクシング 「Save changes」を押すと、以下のように、reindexingへのリンク(黄色)が表示されます。 ...

DrupalでGraphQLを試す

DrupalでGraphQLを試す

概要 DrupalでGraphQLを試してみましたので、その備忘録です。以下の文書が参考になりました。 https://drupal-graphql.gitbook.io/graphql/ Amazon LightsailにインストールされたDrupalを前提とします。 モジュールのインストール 以下のモジュールをインストールします。 https://www.drupal.org/project/graphql ただし、以下のモジュールを事前にインストールする必要がありました。 https://www.drupal.org/project/typed_data 結果、以下により、インストールができました。 cd /home/bitnami/stack/drupal composer require 'drupal/typed_data:^1.0@beta' composer require 'drupal/graphql:^4.4' GUIからのモジュールインストール 関連する以下の3つのモジュール全てにチェックを入れて、インストールしました。 設定 以下にアクセスします。 /admin/config/graphql 「Create server」で、以下のように設定しました。test_serverという名前にしました。 Explore 以下にアクセスします。 /admin/config/graphql/servers/manage/test_server/explorer 以下のような画面に遷移します。 以下のクエリを投げてみます。 { articles { total } } 以下のような結果が得られます。 { "data": { "articles": { "total": 5054 } } } まとめ 今後、独自のスキーマを用いた使用方法についても調査してみたいと思います。参考になりましたら幸いです。

StrapiにGraphQLを追加する

StrapiにGraphQLを追加する

概要 以下の記事で、StrapiをAmazon Lightsail上に立ち上げました。 今回は、GraphQLを追加して、使用してみます。 GraphQLプラグインのインストール 以下を実行しました。backendなどのパスは適宜読み替えてください。 cd /opt/bitnami/apache2/htdocs/backend yarn add @strapi/plugin-graphql そして、アプリを起動します。 yarn develop そして、/graphqlにアクセスすると、以下のような画面が表示されます。 今回、servicesというコンテンツタイプを作成し、titleというフィールドを作成済みでした。なので、以下のようなクエリを発行することで、その一覧やメタデータを取得できました。 # Write your query or mutation here query getServices { services { data { id attributes { title createdAt updatedAt } } } } 以下が結果です。 { "data": { "services": { "data": [ { "id": "1", "attributes": { "title": "Cultural Japan", "createdAt": "2023-04-10T21:59:08.768Z", "updatedAt": "2023-04-10T21:59:12.752Z" } } ] } } } まとめ 次は、Next.jsなどとの連携を試してみたいと思います。

Pythonを使ってDrupalのタクソノミーの登録とコンテンツへの追加

Pythonを使ってDrupalのタクソノミーの登録とコンテンツへの追加

概要 以下のシリーズの続きです。 今回は、タクソノミーの登録とコンテンツへの追加を行います。 タクソノミーの登録 事前に、ne_classというタクソノミーをGUIを通じて作成しました。以下のようなURLで一覧できます。 /jsonapi/taxonomy_term/ne_class 以下、新しいタクソノミーを登録するプログラムです。host, username, passwordは適宜設定してください。 payload = { "data": { "type": "taxonomy_term--ne_class", "attributes": { "name": "干瀬", } } } _type = "ne_class" url = f"{host}/jsonapi/taxonomy_term/{_type}" r = requests.post(url, headers=headers, auth=(username, password), json=payload) r.json() 以下のような結果が得られます。 {'jsonapi': {'version': '1.0', 'meta': {'links': {'self': {'href': 'http://jsonapi.org/format/1.0/'}}}}, 'data': {'type': 'taxonomy_term--ne_class', 'id': '17c70bd6-e6fc-46e2-bb5d-2377ba9c8ab8', ... コンテンツへの追加 事前に、PlaceというコンテンツタイプをGUIを通じて作成しました。また、field_ne_classを作成して、上記のタクソノミーne_classを値の候補として設定しました。 relationshipsのidに先程取得したタクソノミーのidを指定しています。 payload = { "data": { "type": "node--place", "attributes": { "title": "xxx" }, "relationships": { "field_ne_class": { "data": { "type": "taxonomy_term--ne_class", "id": "17c70bd6-e6fc-46e2-bb5d-2377ba9c8ab8", } } } } } _type = "place" url = f"{host}/jsonapi/node/{_type}" r = requests.post(url, headers=headers, auth=(username, password), json=payload) r.json() まとめ タクソノミーの追加やコンテンツへの関連付けも機械的に行うことができそうです。他のよりよい方法もあるかと思いますが、参考になりましたら幸いです。 ...

Pythonを使ってDrupalのコンテンツを更新・削除する

Pythonを使ってDrupalのコンテンツを更新・削除する

概要 以下の記事で、コンテンツの新規登録の方法を記載しました。 今回は、既存のコンテンツの更新・削除を試みます。 アイテムの絞り込み 以下のようなプログラムにより、登録済みのコンテンツを取得することができます。今回は、titleが「更新前のタイトル」のコンテンツを取得しました。res["data"]は配列になります。 username = "xxx" password = "xxx" host = "xxx" query = { "title": "更新前のタイトル" } item_type = "article" filters = [] for key, value in query.items(): filters.append(f'filter[{key}]={value}') filter_str = '&'.join(filters) endpoint = f'{host}/jsonapi/node/{item_type}?{filter_str}' r = requests.get(endpoint, headers=headers, auth=(username, password)) res = r.json() len(res['data']) 更新対象のコンテンツのID取得 730f844d-b476-4485-8957-c33fccb7f8acのようなIDが得られます。 item = res['data'][0] item_id = item['id'] 更新 typeとidを指定して更新します。 ...

Pythonを使ってDrupalにコンテンツを追加する

Pythonを使ってDrupalにコンテンツを追加する

概要 Pythonを使ってDrupalにコンテンツを追加する機会がありましたので、その備忘録です。以下の記事を参考にしました。 https://weimingchenzero.medium.com/use-python-to-call-drupal-9-core-restful-api-to-create-new-content-9f3fa8628ab4 Drupalの準備 Amazon Lightsailに作成しました。以下の記事などが参考になります。 https://annai.co.jp/article/use-aws-lightsail モジュール 以下をインストールします。 HTTP Basic Auth JSON:API RESTful Web Services Serialization JSON:APIの設定変更 以下にアクセスして、設定を変更します。 </admin/config/services/jsonapi> Python {ipアドレス or ドメイン名}、{パスワード}を適宜設定してください。 Amazon Lightsailの場合、初期ユーザ名はuserです。またパスワードは以下のコマンドで確認します。 cat ~/bitnami_application_password import requests from requests.auth import HTTPBasicAuth endpoint = 'http://{ipアドレス or ドメイン名}/jsonapi/node/article' u = 'user' p = '{パスワード}' headers = { 'Accept': 'application/vnd.api+json', 'Content-Type': 'application/vnd.api+json' } payload = { "data": { "type": "node--article", "attributes": { "title": "What's up from Python", "body": { "value": "Be water. My friends.", "format": "plain_text" } } } } r = requests.post(endpoint, headers=headers, auth=(u, p), json=payload) r.text その他 以下のようにnote_typeの登録も試みました。 payload = { "data": { "type": "node_type--node_type", "attributes": { "title": "テスト", "description": "node_typeのテストです。" } } } url = f"{host}/jsonapi/node_type/node_type" r = requests.post(url, headers=headers, auth=(username, password), json=payload) r.json() 結果、以下のように、Method Not Allowedとなりました。 ...

Amazon LightsailでStrapiを動かす(SSL, 独自ドメイン)

Amazon LightsailでStrapiを動かす(SSL, 独自ドメイン)

概要 Amazon LightsailでStrapiを動かす機会がありましたので、その備忘録です。以下の記事を参考にしました。 https://zenn.dev/holykzm/articles/1e54cc25207657 インスタンス Node.jsを選択します。 メモリは1GB以上のものを選択してください。Lightsail上でビルドする場合、メモリ不足でエラーが発生します。 SSL、独自ドメイン 以下を参考にしてください。 https://zenn.dev/nakamura196/articles/5772d6c918508a#独自ドメインの付与 Static IPを付与して、Route 53で独自ドメインを設定し、以下を実行します。 sudo /opt/bitnami/bncert-tool ProxyPassの設定 (より適切な記述箇所があるかと思いますが、)以下を追記します。 /opt/bitnami/apache2/conf/httpd.conf # 末尾に以下を追加 ProxyPass / http://localhost:1337/ ProxyPassReverse / http://localhost:1337/ apacheの再起動 sudo /opt/bitnami/ctlscript.sh restart apache Strapi のインストール cd /opt/bitnami/apache2/htdocs/ npx create-strapi-app@latest backend --quickstart アプリが起動するので、Ctrl+Cなどで一旦停止します。 pm2 pm2のインストール sudo npm install pm2 -g server.jsの作成 cd /opt/bitnami/apache2/htdocs/backend vi server.js /opt/bitnami/apache2/htdocs/backend/server.js const strapi = require('@strapi/strapi'); strapi(/* {...} */).start(); ビルド cd /opt/bitnami/apache2/htdocs/backend NODE_ENV=production npm run build サーバの起動 NODE_ENV=production pm2 start server.js --name strapi 以下のように、strapiを起動できました。 ...

ShExファイルを作成してみる

ShExファイルを作成してみる

概要 ShExは、wikipediaにおいて、以下のように説明されています。 Shape Expressionsは、Resource Description Frameworkを検証および記述するためのデータモデリング言語 このShExファイルの作成を試みましたので、その備忘録です。 shexファイルを作成する 今回、data/tmp/merged.ttlにあるRDFデータを起点とします。shexerを用いて、RDFデータからshexファイルを作成します。 pip install shexer RDFデータ内のクラスの一覧を取得する from rdflib import Graph input_nt_file = "data/tmp/merged.ttl" graph = Graph() graph.parse(input_nt_file, format="turtle") knows_query = """ SELECT DISTINCT ?cls WHERE { ?a a ?cls }""" qres = graph.query(knows_query) target_classes = [] for row in qres: target_classes.append(f"{row.cls}") target_classes 取得したクラスを対象に、処理を行う。 from shexer.shaper import Shaper from shexer.consts import NT, SHEXC, SHACL_TURTLE, TURTLE shaper = Shaper(target_classes=target_classes, input_format=TURTLE, graph_file_input=input_nt_file) output_file = "data/tmp/shapes.shex" shaper.shex_graph(output_file=output_file, acceptance_threshold=0.1) print("Done!") 結果、以下のようなshexファイルが作成されました。 :教育メタデータ { exp:指導要領コード IRI +; # 100.0 % # 12.307692307692308 % obj: IRI. Cardinality: {7} rdf:type [data:教育メタデータ] ; # 100.0 % schema:geo IRI +; # 100.0 % # 21.53846153846154 % obj: IRI. Cardinality: {1} # 12.307692307692308 % obj: IRI. Cardinality: {3} # 12.307692307692308 % obj: IRI. Cardinality: {6} # 10.76923076923077 % obj: IRI. Cardinality: {2} exp:学年 @:学年 +; # 100.0 % # 21.53846153846154 % obj: @:学年. Cardinality: {5} # 16.923076923076923 % obj: @:学年. Cardinality: {1} # 10.76923076923077 % obj: @:学年. Cardinality: {6} # 10.76923076923077 % obj: @:学年. Cardinality: {4} # 10.76923076923077 % obj: @:学年. Cardinality: {3} exp:教科 @:教科 +; # 100.0 % # 18.461538461538463 % obj: @:教科. Cardinality: {8} # 15.384615384615385 % obj: @:教科. Cardinality: {3} # 12.307692307692308 % obj: @:教科. Cardinality: {6} # 12.307692307692308 % obj: @:教科. Cardinality: {4} # 10.76923076923077 % obj: @:教科. Cardinality: {5} rdfs:label xsd:string ; # 100.0 % exp:学習指導案 IRI ; # 100.0 % exp:時代 @:時代 *; # 96.92307692307692 % obj: @:時代. Cardinality: + # 23.076923076923077 % obj: @:時代. Cardinality: {2} # 15.384615384615385 % obj: @:時代. Cardinality: {1} # 15.384615384615385 % obj: @:時代. Cardinality: {3} # 13.846153846153847 % obj: @:時代. Cardinality: {4} # 12.307692307692308 % obj: @:時代. Cardinality: {6} ... shexをTurtle形式に変換する ここから、上記で作成したshexファイルをTurtle形式に変換してみます。 ...

Nuxt3 x babylon.jsで.glbファイルをロードする

Nuxt3 x babylon.jsで.glbファイルをロードする

概要 Nuxt3 x babylon.jsにおいて、.glbファイルのロードを試みた際にエラーが発生しましたので、その備忘録です。 エラーの内容 以下のエラーが発生しました。 Unable to load from ./models/test.glb: importScene of undefined from undefined version: undefined, exporter version: undefinedimportScene has failed JSON parse 対応内容 以下を追加でインストールすることで対応できました。 npm install @babylonjs/loaders 結果、以下のようなjsファイルで表示することができました。 import { Engine, Scene, FreeCamera, Vector3, HemisphericLight, SceneLoader, } from "@babylonjs/core"; import "@babylonjs/loaders/glTF"; const myScene = { engine: null, scene: null, // シーンを作成する関数 createScene: function (canvas) { // エンジンとシーンの初期化 const engine = new Engine(canvas); const scene = new Scene(engine); myScene.engine = engine; myScene.scene = scene; // カメラの設定 const camera = new FreeCamera("camera1", new Vector3(0, 5, -10), scene); camera.setTarget(Vector3.Zero()); camera.attachControl(canvas, true); // 光源の設定 new HemisphericLight("light", Vector3.Up(), scene); // GLBモデルの読み込み SceneLoader.Append( "./models/", "test.glb", scene, function (/*newMeshes*/) { // const mesh = scene.meshes[0]; // シーン内のカメラとライトを作成または更新 scene.activeCamera = null; scene.createDefaultCameraOrLight(true); scene.activeCamera.attachControl(canvas, false); } ); // レンダリングループ engine.runRenderLoop(() => { scene.render(); }); }, }; export default myScene; まとめ 同様のエラーでお困りの方の参考になりましたら幸いです。 ...

vue3とbabylon.jsの双方向のやりとり例

vue3とbabylon.jsの双方向のやりとり例

概要 vue3とbabylon.jsの双方向のやりとりを行うプログラムを試作しました。以下のリンク先で内容をご確認いただけます。 https://youtube.com/shorts/BIdj-3T2_z8 デモサイト https://nakamura196.github.io/nuxt3-babylonjs/9 ソースコード https://github.com/nakamura196/nuxt3-babylonjs/blob/main/pages/9/index.vue まとめ 参考になりましたら幸いです。

Hugging Face Spaceを用いたNDL古典籍OCRのウェブアプリ

Hugging Face Spaceを用いたNDL古典籍OCRのウェブアプリ

概要 Hugging Face Spaceを用いたNDL古典籍OCRのウェブアプリを作成しました。以下でお試しいただけます。画像アップロードして、1分程度すると、OCR結果のテキストとJSONデータが表示されます。 https://huggingface.co/spaces/nakamura196/ndl_kotenseki_ocr 本アプリの作成にあたっては、以下の記事を参考にさせていただきました。 https://qiita.com/relu/items/e882e23a9bd07243211b 使い分け NDL古典籍OCRを試す環境として、Google Colabを用いたチュートリアルを別途用意しています。 上記では無料でGPUを使用することができるため、高速なOCR処理が可能です。一方、ノートブックの初回起動時に、関連するライブラリやモデルのダウンロードを行うため、4分程度のセットアップ時間がかかってしまう点等に課題があります。 一方、今回Hugging Face Spaceを用いた作成したアプリケーションでは、72時間連続して使用されない(2023年2月時点)限り、OCR処理を即座に実行することが可能です。さらに、Web APIによる利用も可能といった点が挙げられます。(APIによる利用については後述します。)ただし、無料枠ではGPUが使用できないため、1画像あたり1分程度の処理時間がかかる点が課題です。(有料枠でGPUを使用することもできます。) APIによる利用 APIによる利用例を試すことができるノートブックを用意しました。504 Gateway Time-outというエラーが発生してしまう場合もありますが、参考になりましたら幸いです。 https://colab.research.google.com/github/nakamura196/ndl_ocr/blob/main/GradioのAPIを用いたNDL古典籍OCRの例.ipynb まとめ NDL古典籍OCRの精度(≠速度)を試してみる場合など参考になりましたら幸いです。

NDL古典籍OCRをAmazon EC2のCPU環境で実行する

NDL古典籍OCRをAmazon EC2のCPU環境で実行する

概要 NDL古典籍OCRをAmazon EC2のCPU環境で実行してみましたので、その備忘録です。高額になりがちなGPU環境を用意せずに実行できる点が利点ですが、1画像あたり30秒から1分程度の時間がかかりますので、ご注意ください。 本環境の構築にあたり、以下の記事を参考にしています。 https://qiita.com/relu/items/e882e23a9bd07243211b インスタンス クイックスタートのUbuntuを選択します。 インスタンスタイプについえは、t2.medium以上をおすすめします。それより小さいインスタンスだと、エラーが発生しました。 サーバ内での設定 sshでログインし、以下を実行します。 sudo apt-get update && sudo apt-get upgrade -y sudo apt -y install build-essential sudo apt -y install libgl1-mesa-dev libglib2.0-0 sudo apt -y install unzip sudo apt install -y python3-pip sudo apt install -y python3.10-venv python3 -m venv app source app/bin/activate pip install --upgrade pip git clone https://github.com/ndl-lab/ndlkotenocr_cli.git cd ndlkotenocr_cli vi requirements.txt requirements.txtを開き、scikit-imageのバージョンを除く。また、torchとtorchvisionを追加する。 click lmdb==1.2.1 natsort==7.1.1 nltk==3.6.6 numpy==1.22.4 albumentations==1.2.1 opencv-python==4.6.0.66 protobuf==3.19.6 pyyaml scikit-image # scikit-image==0.16.2 scipy==1.7.3 lightgbm==3.3.2 transformers==4.19.1 pandas==1.3.5 mmcls==0.23.1 mmdet==2.25.0 datasets==2.2.1 jiwer==2.3.0 wheel torch torchvision 引き続き以下を実行する。 ...

Nuxt.jsとNext.jsの比較

Nuxt.jsとNext.jsの比較

Nuxt.jsとNext.jsは、どちらもJavaScriptのフレームワークで、Vue.jsとReact.jsの上に構築されています。それぞれのフレームワークには独自の利点がありますが、Nuxt.jsがNext.jsに比べて優れているとされる点をいくつか挙げます。 1. Vue.jsの利点: Nuxt.jsはVue.jsをベースとしているため、Vue.jsの利点を引き継いでいます。Vue.jsは、コンポーネントの構造がシンプルで、学習曲線が緩やかであることが評価されています。 2. ディレクトリベースのルーティング: Nuxt.jsは、ディレクトリ構造を使ってルーティングを自動生成します。これにより、開発者はルーティング設定を手動で行う必要がなくなり、開発効率が向上します。 3. Vuexの統合: Nuxt.jsでは、Vuex(Vue.jsの状態管理ライブラリ)がデフォルトで統合されています。これにより、状態管理が容易になります。 4. ミドルウェアのサポート: Nuxt.jsでは、ミドルウェアを利用してルートやページにカスタムロジックを追加できます。これにより、開発者はアプリケーションの振る舞いを簡単にカスタマイズできます。 5. モジュールシステム: Nuxt.jsにはモジュールシステムがあり、コミュニティで開発された機能を簡単に追加できます。これにより、開発者はアプリケーションの拡張性を向上させることができます。 ただし、どちらのフレームワークが優れているかは、プロジェクトの要件や開発者のスキルセット、好みによって異なります。Next.jsもReact.jsのエコシステムやサーバーサイドレンダリング(SSR)、静的サイト生成(SSG)などの機能を持っており、多くの開発者に支持されています。最終的には、どちらのフレームワークがプロジェクトに適しているかを慎重に検討することが重要です。

正規URLとは? (canonicalUrl)

正規URLとは? (canonicalUrl)

canonical URLとは、同じコンテンツを指す異なるURLが存在する場合に、その中から1つの「正規」なURLを選ぶことです。これは検索エンジンがコンテンツの重複を防ぎ、ウェブページの検索順位に悪影響を与えることなく、ウェブページの重要度を正確に評価できるようにするために使用されます。 例えば、以下のようなURLがあったとします。 1. http://example.com/page 2. http://www.example.com/page 3. https://example.com/page 4. https://www.example.com/page これらのURLはすべて同じコンテンツを指しているとしても、検索エンジンはそれらを異なるページとして扱うことがあります。canonical URLは、HTMLの`

Fuse.jsを使用した完全不一致検索(GPT-4による解説)

Fuse.jsを使用した完全不一致検索(GPT-4による解説)

はじめに 以前に以下の記事を執筆しましたが、GPT-4による解説の方が有用でしたので紹介します。 完全不一致検索を JavaScript で実装する方法 Fuse.js は、クライアントサイドで動作する軽量なファジーサーチライブラリです。ただし、今回の目的である完全不一致検索 には向いていません。代わりに、JavaScript の Array メソッドを使って簡単に実装できます。 完全不一致検索の例 次の例では、filter メソッドを使って完全不一致検索を行います。 const data = [ { title: 'Example Title 1', content: 'This is an example content for the first item.', }, { title: 'Example Title 2', content: 'This is an example content for the second item.', }, // ... 他のデータ ]; const searchTerm = 'Example Title 1'; const results = data.filter( (item) => item.title !== searchTerm && item.content !== searchTerm ); console.log(results); この例では、data 配列から searchTerm と完全に一致しない要素をフィルタリングしています。title と content の両方が searchTerm と一致しない場合、要素が結果の配列に含まれます。 このように、JavaScript のネイティブな Array メソッドを使って完全不一致検索を実装できます。 ...

TEI/XMLファイルからrespStmtのnameの値を抽出する方法(GPT-4による解説)

TEI/XMLファイルからrespStmtのnameの値を抽出する方法(GPT-4による解説)

TEI/XMLファイルからrespStmtのnameの値を抽出する方法: PythonでBeautifulSoupとElementTreeを使ったアプローチ この記事では、PythonのBeautifulSoupとElementTreeを使って、TEI/XMLファイルからrespStmtのnameの値を抽出する方法を紹介します。 方法1: ElementTreeを使う まず、Pythonの標準ライブラリであるxml.etree.ElementTreeを使って、respStmtのnameの値を抽出します。 import xml.etree.ElementTree as ET # XMLファイルを読み込む tree = ET.parse('your_file.xml') root = tree.getroot() # 名前空間を定義 ns = {'tei': 'http://www.tei-c.org/ns/1.0'} # respStmtのnameの値を抽出 name = root.find('.//tei:respStmt/tei:name', ns) # nameのテキストを表示 if name is not None: print(name.text) else: print("nameタグが見つかりませんでした。") 方法2: BeautifulSoupを使う 次に、BeautifulSoupを使って、respStmtのnameの値を抽出します。まず、beautifulsoup4とlxmlライブラリがインストールされていることを確認してください。インストールされていない場合は、以下のコマンドでインストールできます。 pip install beautifulsoup4 lxml 以下のコードで、BeautifulSoupを使ってrespStmtのnameの値を抽出できます。 from bs4 import BeautifulSoup # XMLファイルを読み込む with open('your_file.xml', 'r', encoding='utf-8') as file: content = file.read() # BeautifulSoupオブジェクトを作成 soup = BeautifulSoup(content, 'lxml-xml') # respStmtのnameの値を抽出 name = soup.find('respStmt').find('name') # nameのテキストを表示 if name: print(name.text) else: print("nameタグが見つかりませんでした。") どちらの方法でも、respStmtのnameの値をPythonで簡単に抽出することができます。あなたのプロジェクトに適した方法を選んでください。