🎄teratailクリスマスプレゼントキャンペーン2024🎄』開催中!

\teratail特別グッズやAmazonギフトカード最大2,000円分が当たる!/

詳細はこちら
Node.js

Node.jsとはGoogleのV8 JavaScriptエンジンを使用しているサーバーサイドのイベント駆動型プログラムです。

JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

jQuery

jQueryは、JavaScriptライブラリのひとつです。 簡単な記述で、JavaScriptコードを実行できるように設計されています。 2006年1月に、ジョン・レシグが発表しました。 jQueryは独特の記述法を用いており、機能のほとんどは「$関数」や「jQueryオブジェクト」のメソッドとして定義されています。

HTML

HTMLとは、ウェブ上の文書を記述・作成するためのマークアップ言語のことです。文章の中に記述することで、文書の論理構造などを設定することができます。ハイパーリンクを設定できるハイパーテキストであり、画像・リスト・表などのデータファイルをリンクする情報に結びつけて情報を整理します。現在あるネットワーク上のほとんどのウェブページはHTMLで作成されています。

Q&A

解決済

3回答

2856閲覧

NodeでjQuery使用

Fujiman

総合スコア41

Node.js

Node.jsとはGoogleのV8 JavaScriptエンジンを使用しているサーバーサイドのイベント駆動型プログラムです。

JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

jQuery

jQueryは、JavaScriptライブラリのひとつです。 簡単な記述で、JavaScriptコードを実行できるように設計されています。 2006年1月に、ジョン・レシグが発表しました。 jQueryは独特の記述法を用いており、機能のほとんどは「$関数」や「jQueryオブジェクト」のメソッドとして定義されています。

HTML

HTMLとは、ウェブ上の文書を記述・作成するためのマークアップ言語のことです。文章の中に記述することで、文書の論理構造などを設定することができます。ハイパーリンクを設定できるハイパーテキストであり、画像・リスト・表などのデータファイルをリンクする情報に結びつけて情報を整理します。現在あるネットワーク上のほとんどのウェブページはHTMLで作成されています。

0グッド

0クリップ

投稿2018/09/16 03:11

編集2018/09/16 03:14

deprecateという感じですがNode環境ででjQueryを使えるようにしておく必要があり
以下のようにしましたが、jQueryのメソッドチェーンがfind()以降、
つなげることができません。jQueryのオブジェクトが返ってきていないようです

JavaScript

1/* 2 input.html の内容の一部を変更して output.html に書き込むというものです 3*/ 4 5var $ = require('jquery'); 6var fs = require('fs'); 7var jsdom = require('jsdom'); 8const { JSDOM } = jsdom; 9 10fs.readFile(__dirname + '/input.html', function (err, data) { 11 if (err) throw err; 12 let body = data.toString(); 13 const dom = new JSDOM(body); 14 15 // Error(jQuery) 16 let newBody = $(dom.window.window).find('h1')[0].text('Hello World').parents('html')[0].outerHTML; 17 18 fs.writeFile(__dirname + '/output.html', newBody, 'utf-8', function(){ 19 if (err) throw err; 20 console.log('done'); 21 }); 22});

$(dom.window.window).find('h1')まではブレークさせみてみると
'Array(1) [HTMLHeadingElement]'となってて
DOMそのものは取得できているようなのですが・・・
エラー発生箇所を以下のように書き換えると問題なく完了します

JavaScript

1 // Done well(DOM) 2 dom.window.document.querySelector("h1").innerHTML = 'Hello World'; 3 const newBody = dom.window.document.querySelector('html').outerHTML;

##(補足)
上記コード内の'$(dom.window.window)'の部分ですが jsdom の仕様を
見ていたりして思いついてやってます。こうしないと、そもそもjQueryが
「jQuery requires a window with a document」のエラーになります

もちろんこのコードに限ったことではないのですが
普通にjQueryが使用できる状況を得るにはどうすればいいでしょうか?

##(環境)
OSX HighSierra v.10.13.6
VS CODE v.1.27.2
Node v.8.6.0
jsdom v.12.0.0
jquery v.3.3.1

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答3

0

単にjQueryでのHTML操作方法が誤っています。

let newBody = $(dom.window.window).find('h1')[0].text('Hello World').parents('html')[0].outerHTML;

これをばらしてみましょうか

JavaScript

1let newBody = $(dom.window.window) 2 .find('h1')[0] // <-原因はこの[0] 3 .text('Hello World') 4 .parents('html')[0] 5 .outerHTML;

jQueryオブジェクトは、配列アクセスを行うとHTMLのネイティブなエレメントに変換されます。
つまり、この時点でjQueryオブジェクトではなくなります。

続く.text(str).parents('html')はこれ全部jQueryオブジェクト想定ですよね?
最後の.outerHTMLのみHTMLのエレメント想定です

jQueryにはjQueryオブジェクト1個にアクセスする方法としてgetメソッドが存在していたはずです。
.get() - jQueryドキュメント公式

つまりこう書き直せば上手くいくんじゃないですかね?知らんけど。

JavaScript

1let newBody = $(dom.window.window) 2 .find('h1') 3 .get(0) 4 .text('Hello World') 5 .parents('html')[0] 6 .outerHTML;

投稿2018/09/16 03:49

miyabi-sun

総合スコア21203

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Fujiman

2018/09/16 04:38

「jQueryオブジェクトは、配列アクセスを行うとHTMLのネイティブなエレメントに変換される」というのは知りませんでした。ありがとうございます。ただ、やってみたのですが以下のエラーになります。 どうやら「$(dom.window.window) .find('h1')」コレ自体がフェイクjQueryみたいです(w TypeError: $(...).find(...).get is not a function
guest

0

ベストアンサー

Node環境(global.documentが定義されていない環境)でrequire('jquery')を実行した場合、戻り値は普段のjQuery関数ではなく、引数にwindowオブジェクトを与えるとjQuery関数を返す関数になるようです。

javascript

1const jqFactory = require('jquery'); 2const $ = jqFactory(windowObject);

なので、普段のjQuery関数$を得るには、質問文のコードで言えばdom.windowを指定する必要があります。
また、outerHTMLを取得する行にも修正を加える必要があります。

javascript

1// 修正前 2let newBody = $(dom.window.window).find('h1')[0].text('Hello World').parents('html')[0].outerHTML; 3 4// 修正後 5let newBody = $(dom.window.document).find('h1').eq(0).text('Hello World').parents('html')[0].outerHTML;

最終的なコードは下記の通りとなります。(Node v8.11.4で動作確認済)

javascript

1var jqFactory = require('jquery'); 2var fs = require('fs'); 3var jsdom = require('jsdom'); 4const { JSDOM } = jsdom; 5 6fs.readFile(__dirname + '/input.html', function (err, data) { 7 if (err) throw err; 8 let body = data.toString(); 9 const dom = new JSDOM(body); 10 const $ = jqFactory(dom.window); 11 12 let newBody = $(dom.window.document).find('h1').eq(0).text('Hello World').parents('html')[0].outerHTML; 13 14 fs.writeFile(__dirname + '/output.html', newBody, 'utf-8', function(){ 15 if (err) throw err; 16 console.log('done'); 17 }); 18});

投稿2018/09/16 12:28

reosablo

総合スコア339

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

reosablo

2018/09/16 12:59

getメソッドは配列アクセスと同じくHTMLのネイティブなエレメントが返ってきてしまうので、eqメソッドを使うことになります。 https://api.jquery.com/eq/#eq-index
Fujiman

2018/09/16 12:59

ありがとうございます。うまく処理できるようになりました。 普通(私のリサーチ力では)「戻り値は普段のjQuery関数ではなく」 facotoryが返ってるって・・・わかりません 教えてもらえなかったら行きつかなかったと思います(感謝)
reosablo

2018/09/16 13:16

実は私も、この質問について調べる中でjQueryのソースコードを見るまでは知りませんでした。公式の説明もちょうどいいものが見つからなかったので、Web検索だけだと見つからなかったかもしれません。私自身勉強になるよいきっかけになりました。
guest

0

getを使う方法が回答されているので別解でも書いときます。

js

1let newBody = $($(dom.window.window).find('h1')[0]) 2 .text('Hello World') 3 .parents('html')[0] 4 .outerHTML;

めっちゃ格好悪いですが、これでもいけるはずですね。

投稿2018/09/16 04:03

spookybird

総合スコア1803

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Fujiman

2018/09/16 04:40

これ、私もやってみたのですがやはり以下のエラーになります Error: jQuery requires a window with a document
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.36%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問