20210416のJavaに関する記事は6件です。

Azure FunctionsにてJavaプログラムをイゴかして、Bing News Search APIで取得したとれたて新鮮ニュースを毎朝母にLINEメッセージでおくりつける

はじめに Java楽しんでいますか この記事はJava開発者のためのAzure入門というキャンペーンへの投稿記事です この記事では、Azure Functionsを使って、朝06:30にJavaのプログラムを動かして以下のことを行います Bing News Search APIにて新鮮とれたてニュースを取得します LINEのMessaging APIを使って、Bing News Search APIで取得した新鮮とれたてニュースと「おはようございます」というあいさつを母が属するグループへ送りつけます 制作背景 最近、seventyになんなんとする母がスマートフォンを買いました 買い替えた理由は、「FOMAが終わると聞いたから早めに慣れておきたい」というものです 表向きもっともらしいことをいっていますが、本当はまわりの人がシュッとやっているのをみて母自身がやってみたくなっただけなのだとおもいます スマートフォンはファッションなのです パカパカの携帯電話はいやだ、あたいもスマホがいい いくつになっても女心は枯れてはいないとでも申しましょうか ショップに行ったら、本人は買いたいと言っているのに店員からは止められる始末 値段の高い端末しかショップにはおいてなくてお値打ち価格のものは入荷まで1ヶ月かかると言われて、「もう一度検討する」と言って帰りました 母のスマホを買いたい気持ちは止められるはずもなく、docomo Online Shopを利用したら2日後に届いて初期設定をやってあげました はじめてスマホプランです 1GB/月で全然いいんです 余ります 4/16現在、残りは0.98GBありました 実家にインターネットは引いてありまして、Wi-Fiルーターはありますし、ほとんど家からでることはありませんし、外にでかけるときもスマホは忘れておいていくので1GBでギガは十分足ります そもそも母には意味がわかりませんし、いいんです 外で動画みたりするわけないし、そもそも動画アプリの起動ができるかあやしいし $\huge{5G}$ 対応機種です 実家はど田舎なので、5Gとか来ていませんが4G圏内でよかったよかった そんな母が、「LINEは難しい」と言います LINEと接する機会を増やしたほうがいいだろうということではじめは私が手打ちでメッセージを送っていました ただ、だんだん 面倒くさくなってきました $\huge{面倒くさくなってきました}$ そこでボット に代行してもらうことにしました ちなみに母にボットと言っても通じないので「ロボット」が送っていると説明しています こういう用途に、Azure Functionsはうってつけだとおもいます Nervesならできるもん! ということで、Elixirというプログラミング言語をつかって、Raspberry Piで動かすのがいま一番私が得意とすることですが、それだとイベントに参加できないし、たまには違うことやってみるのが「そこがいいんじゃない!1」ということでAzure FunctionsでJavaのプログラムをイゴかしたいとおもいます まだ読んだことはありませんが、みうらじゅんさんの親孝行プレイに通じるものがあるのではないかと勝手におもっています 準備 Azure Functions(Java)を利用するための準備運動 にまとめました もうひとつ準備が必要です ローカルでの Azure Storage の開発に Azurite エミュレーターを使用するを参考に、Azurite オープンソース エミュレーターをインストールしておいてください Azurite Visual Studio Code の拡張機能をインストールして実行するでインストールしました VSCodeの右下のほうに [Azurite Blob Service] と表示されているものがあるはずでそれを迷わず押しておくとよいです 以下、 の記事に書いていることはスミ2の前提で書いていきます つくる 前置きが四の五の多かったですが、ここから先はあっさり楽勝です クイックスタート: コマンド ラインから Azure に Java 関数を作成する という公式の手順を適宜読み替えてすすめていきます ① プロジェクトをつくる ローカル関数プロジェクトを作成する mvn archetype:generate -DarchetypeGroupId=com.microsoft.azure \ -DarchetypeArtifactId=azure-functions-archetype \ -DjavaVersion=11 \ -DgroupId=tokyo.torifuku \ -DartifactId=torifuku-functions \ -Dtrigger=TimerTrigger TimerTriggerの指定は、こちらの記事にて教えてもらいました Azure Functions(Java)のTimerTriggerをローカルで動かしてみる ありがとうございます! ② プログラム書く、書く、書く pom.xml <dependency> <groupId>com.linecorp.bot</groupId> <artifactId>line-bot-api-client</artifactId> <version>4.3.0</version> </dependency> <dependency> <groupId>com.linecorp.bot</groupId> <artifactId>line-bot-model</artifactId> <version>4.3.0</version> </dependency> <dependency> <groupId>com.google.code.gson</groupId> <artifactId>gson</artifactId> <version>2.8.5</version> </dependency> </dependencies> pom.xml <!-- function app name --> <appName>${functionAppName}</appName> <!-- function app resource group --> - <resourceGroup>java-functions-group</resourceGroup> + <resourceGroup>java-torifuku-functions-20210411122137476</resourceGroup> <!-- function app service plan name --> <appServicePlanName>java-functions-app-service-plan</appServicePlanName> <!-- function app region--> <!-- refers https://github.com/microsoft/azure-maven-plugins/wiki/Azure-Functions:-Configuration-De tails#supported-regions for all valid values --> - <region>westus</region> + <region>japaneast</region> <!-- function pricingTier, default to be consumption if not specified --> <!-- refers https://github.com/microsoft/azure-maven-plugins/wiki/Azure-Functions:-Configuration-Details#supported-pricing-tiers for all valid values --> <!-- <pricingTier></pricingTier> --> @@ -76,7 +94,7 @@ <!-- <disableAppInsights></disableAppInsights> --> <runtime> <!-- runtime os, could be windows, linux or docker--> - <os>windows</os> + <os>linux</os> <javaVersion>11</javaVersion> <!-- for docker function, please set the following parameters --> <!-- <image>[hub-user/]repo-name[:tag]</image> --> windowsだと、Bing News Search APIで取得したデータが文字化けしていたのでlinuxにしました 他のもっといい解決方法があるかもしれません とりあえず母親に送りつけることができればいいのでOSは問いません クイック スタート:Java と Bing News Search REST API を使用してニュース検索を実行する リンク先を参考にしてつくりました ほぼ同じです こちらもMicrosoft様のサービスです ありがとうございます! src/main/java/tokyo/torifuku/BingNewsSearch.java package tokyo.torifuku; import java.io.InputStream; import java.net.URL; import java.net.URLEncoder; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.Scanner; import javax.net.ssl.HttpsURLConnection; import com.google.gson.Gson; import com.google.gson.GsonBuilder; import com.google.gson.JsonObject; import com.google.gson.JsonParser; public class BingNewsSearch { // Add your Bing Search V7 subscription key to your environment variables. static String subscriptionKey = System.getenv("BING_SEARCH_V7_SUBSCRIPTION_KEY"); // Add your Bing Search V7 endpoint to your environment variables. static String endpoint = "https://api.bing.microsoft.com/v7.0/news/search"; public static SearchResults searchNews(String searchQuery) throws Exception { // Construct URL of search request (endpoint + query string) URL url = new URL(endpoint + "?q=" + URLEncoder.encode(searchQuery, "UTF-8") + "&setLang=ja-JP" + "&mkt=ja-JP"); HttpsURLConnection connection = (HttpsURLConnection)url.openConnection(); connection.setRequestProperty("Ocp-Apim-Subscription-Key", subscriptionKey); // Receive JSON body InputStream stream = connection.getInputStream(); Scanner scanner = new Scanner(stream); String response = scanner.useDelimiter("\\A").next(); JsonObject jsonResponse = new JsonParser().parse(response).getAsJsonObject(); // Construct result object for return SearchResults results = new SearchResults(new HashMap<String, String>(), jsonResponse); // Extract Bing-related HTTP headers Map<String, List<String>> headers = connection.getHeaderFields(); for (String header : headers.keySet()) { if (header == null) continue; // may have null key if (header.startsWith("BingAPIs-") || header.startsWith("X-MSEdge-")) { results.relevantHeaders.put(header, headers.get(header).get(0)); } } scanner.close(); stream.close(); return results; } // Pretty-printer for JSON; uses GSON parser to parse and re-serialize public static String prettify(JsonObject json) { Gson gson = new GsonBuilder().setPrettyPrinting().create(); return gson.toJson(json); } } src/main/java/tokyo/torifuku/SearchResults.java package tokyo.torifuku; import java.util.HashMap; import com.google.gson.JsonArray; import com.google.gson.JsonObject; public class SearchResults { HashMap<String, String> relevantHeaders; JsonObject jsonResponse; SearchResults(HashMap<String, String> headers, JsonObject json) { relevantHeaders = headers; jsonResponse = json; } public String topNews() { JsonArray array = jsonResponse.getAsJsonArray("value"); JsonObject first = array.get(0).getAsJsonObject(); String name = first.get("name").getAsString(); String url = first.get("url").getAsString(); return name + "\n\n" + url; } } LINEのメッセージをおくる プッシュメッセージを送るのJavaのコードを参考に書きます src/main/java/tokyo/torifuku/Postman.java package tokyo.torifuku; import com.linecorp.bot.model.PushMessage; import com.linecorp.bot.model.message.TextMessage; import com.linecorp.bot.client.LineMessagingClient; import java.util.concurrent.ExecutionException; public class Postman { public void post(String message) { final LineMessagingClient client = LineMessagingClient .builder(System.getenv("LINE_CHANNEL_ACCESS_TOKEN")) .build(); final TextMessage textMessage = new TextMessage(message); final PushMessage pushMessage = new PushMessage( System.getenv("LINE_TO"), textMessage); try { client.pushMessage(pushMessage).get(); } catch (InterruptedException | ExecutionException e) { e.printStackTrace(); return; } } } 定期的に実行するrunメソッド src/main/java/tokyo/torifuku/Function.java package tokyo.torifuku; import java.time.*; import com.microsoft.azure.functions.annotation.*; import com.microsoft.azure.functions.*; /** * Azure Functions with Timer trigger. */ public class Function { /** * This function will be invoked periodically according to the specified schedule. */ @FunctionName("Function") public void run( @TimerTrigger(name = "timerInfo", schedule = "0 30 21 * * *") String timerInfo, final ExecutionContext context ) { context.getLogger().info("Java Timer trigger function executed at: " + LocalDateTime.now()); Postman kevin = new Postman(); kevin.post("おはようございます"); SearchResults result; try { result = BingNewsSearch.searchNews(""); context.getLogger().info(BingNewsSearch.prettify(result.jsonResponse)); String topNews = result.topNews(); context.getLogger().info(topNews); kevin.post(topNews); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } } } scheduleはrunメソッドをRunさせる時間をUTCで指定しています 上の例ですと日本時間の06:30に送りつけることになります 朝は05:00くらいから母は起きだしてごそごそしているので問題ないです Postmanのインスタンス名はもちろんkevinにしました3 城戸利成(元オートレース選手)と迷ったのですが、わかる人が少ないかなあとおもいまして世界的スターのほうを採用しました4 設定値 BING_SEARCH_V7_SUBSCRIPTION_KEY LINE_CHANNEL_ACCESS_TOKEN LINE_TO local.settings.json { "IsEncrypted": false, "Values": { "AzureWebJobsStorage": "UseDevelopmentStorage=true", "FUNCTIONS_WORKER_RUNTIME": "java", "BING_SEARCH_V7_SUBSCRIPTION_KEY": "secret", "LINE_CHANNEL_ACCESS_TOKEN": "secret", "LINE_TO": "secret" } } ③ ローカルでイゴかす 関数をローカルで実行する 待ちきれない場合は、scheduleの値を調整してください mvn clean package mvn azure-functions:run ④ デプロイする Azure 関数をデプロイする mvn clean package azure-functions:deploy 設定値を設定しておいてください BING_SEARCH_V7_SUBSCRIPTION_KEY LINE_CHANNEL_ACCESS_TOKEN LINE_TO 以上で、毎朝06:30にBing News Search APIで取得したとれたて新鮮ニュースがLINEメッセージとして配信されるはずです Wrapping up とても簡単に親孝行ができるようになりました Azureの利用料はほとんどかかっていません リソース グループをわけているのですが0円な気がします まだ使いはじめて1年以内のアカウントなので無料枠の適用があるのかもしれません みなさんもAzure Functionsを使って、お手軽になにかの定期実行をしてみてはいかがでしょうか Happy coding!!! 最後に 私はElixirというプログラミング言語が好きです ここからは同じことをElixirでやってみます プロジェクトをつくる $ mix new good_son --sup $ cd good_son mix.exs defp deps do [ {:httpoison, "~> 1.8"}, {:jason, "~> 1.2"}, {:quantum, "~> 3.0"} ] end $ cd good_son $ mix deps.get プログラムを書く 詳しい解説はしますまい 感じてください lib/good_son/scheduler.ex defmodule GoodSon.Scheduler do use Quantum, otp_app: :good_son end lib/good_son/application.ex defmodule GoodSon.Application do # See https://hexdocs.pm/elixir/Application.html # for more information on OTP Applications @moduledoc false use Application @impl true def start(_type, _args) do children = [ # Starts a worker by calling: GoodSon.Worker.start_link(arg) # {GoodSon.Worker, arg} GoodSon.Scheduler # add ] # See https://hexdocs.pm/elixir/Supervisor.html # for other strategies and supported options opts = [strategy: :one_for_one, name: GoodSon.Supervisor] Supervisor.start_link(children, opts) end end Bing News Search lib/good_son/bing_news_search.ex defmodule GoodSon.BingNewsSearch do @subscriptionKey "secret" def top_news do search() |> Map.get("value") |> Enum.at(0) end def search do "https://api.bing.microsoft.com/v7.0/news/search?q=&setLang=ja-JP&mkt=ja-JP" |> HTTPoison.get!("Ocp-Apim-Subscription-Key": @subscriptionKey) |> Map.get(:body) |> Jason.decode!() end end LINE lib/good_son/line.ex defmodule GoodSon.Line do @to "secret" @channel_access_token "secret" def push(msg \\ "Hello") do body = %{ to: @to, messages: [ %{ type: "text", text: msg } ] } |> Jason.encode!() HTTPoison.post!( "https://api.line.me/v2/bot/message/push", body, "Content-Type": "application/json", Authorization: "Bearer #{@channel_access_token}" ) end end 06:30に実行する関数 lib/good_son.ex defmodule GoodSon do def run do GoodSon.Line.push("おはようございます") %{"name" => name, "url" => url} = GoodSon.BingNewsSearch.top_news() "#{name}\n\n#{url}" |> GoodSon.Line.push() end end config/config.exs import Config config :good_son, GoodSon.Scheduler, jobs: [ {"30 21 * * *", {GoodSon, :run, []}} ] 実行 $ iex -S mix とりあえずローカル(macOS)でイゴくところまででこの記事は終わります ぜひ次は、@erinさんのAzure FunctionsをElixirで みたいなことをしたいです Nervesは得意としておりますし楽しいのですが、いつか自分の手元のハードウェア(Raspberry Pi 2)は壊れることがあるでしょうし、そういうことはクラウドサービスにまかせチャオ5 というのはすごく便利です ありがとうございます! もう一度最後の最後に Elixirって何よ という方へ 最後はがっつりElixirでしめました 2020/12/26時点くらいのスクリーンショット Elixirについてもっと知りたい方は下記の本をオススメします プログラミングElixir(第2版) Elixir実践ガイド elixir.jp Slackの#autoracexというところに私は入り浸っておりますのでお気軽にお声がけください 勉強会が頻繁に行われています 私がよく参加している勉強会です autoracex 【毎週月曜】 主催 Sapporo.beam  【毎週水曜】 OkazaKirin.beam 【毎週木曜】 fukuoka.ex/kokura.ex 【毎月2~3回】 NervesJP  【毎月1回】 (@piacerex さん作 ) 2021年本屋大賞 『発掘部門』 「超発掘本!」の『「ない仕事」の作り方』 より ↩ 昔、銀牙 -流れ星 銀-という犬の漫画がありました。駄菓子屋でカードを売っていて、その中に当り?のカードがあるわけです。当りを引くと何をもらえたのかは忘れましたが、きなこ餅だかもう一枚だかをもらえました。その店の婆さんは景品と交換済みであることをわかるように油性マジックでスミと書いてくださっていたことをおもいだしました。ああいうカードで子供のときはたくさん集めていたわけですがどこに行ってしまったのでしょうね。 ↩ ポストマンの主演ケビン・コスナーさん ↩ 城戸利成選手のことです。競争車名に「ポストマン」を使われていたことがありました。第20回日本選手権オートレースにおいて優出を果たしているすごい選手です。 ↩ https://www.honda.co.jp/ciao/ ↩
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

基本データ型と参照型の違い

基本データ型と参照型の違い データ型 変数を用意する場合、どのような値を格納するのかデータ型で指定します。 Java言語のデータ型には大きく分けて基本データ型と参照型があります。 基本データ型 基本データ型には以下の8種類があります。 データ型 意味 サイズ byte 符号つき整数 8ビット short 符号つき整数 16ビット int 符号つき整数 32ビット long 符号つき整数 64ビット float 浮動小数点数 32ビット double 浮動小数点数 64ビット char Unicodeで表現できる1文字 16ビット boolean 真偽値 1ビット 参照型 参照型は以上8つの以外の型です。 Stringや配列を指します。 基本データ型と参照型の違い 基本データ型は変数に直接、値が代入されます。 一方、参照型はメモリ上のアドレスが代入されます。 基本データ型での動作 次のサンプルコードを見てください int a = 1; int b = a; a = 0; console.log(a); // 結果 0 console.log(b); // 結果 1 変数aと変数bにはそれぞれ直接値が代入されます。 よって、変数aに0を代入しても変数bの値には何の影響もありません。 参照型での動作 では、参照型の場合どのような動作をするのでしょうか? int[] a = {1, 2, 3} int[] b = a; a[0] = 0; console.log(a); // 結果 {0, 2, 3} console.log(b); // 結果 {0, 2, 3} これが参照型の特徴です。 配列bには{1, 2, 3}ではなく、配列aが参照しているメモリ上のアドレスが格納されます。 よって、配列aの変更は配列bにも影響します。 同じように、配列bの変更も配列aに影響します。 基本型と参照型ではこのような違いがあることを覚えておきましょう。 まとめ ・基本データ型は8種類存在する(byte,short,int,long,float,double,char)。 ・String型は上記の8種類意外の型。 ・基本データ型は変数に直接、値が代入される。 ・参照型は変数にアドレスが代入される。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

フレームワークを学びながらJavaをマスターする 

コメント 継続してやって行きたいと思います。 TakeAway 完了条件 改訂版がついてる場合 要旨 ものづくりしながらJavaをマスターする。フレームワーク自体を学ぶ やること・やらないこと やらないこと Java8以降 業務の仕様 データベース関連 やること フレームワーク インプット フレームワーク Javaフレームワーク開発入門 木村 聡 アウトプット 内容 目次 ・読んでみて ・TakeAway chap2 参考アドレス https://qiita.com/KeithYokoma/items/9e692808095acf560bc9 リフレクションの練習 public class Main { private int x; { x = 5; } } import java.lang.reflect.*; public class ex1 { public static void main(String[] args) { try { Main myObj = new Main(); // System.out.println("x = " +myObj.x); // Main m = new Main(); Field f = Main.class.getDeclaredField("x"); f.setAccessible(true); // 取得 System.out.println("x = " + f.get(myObj)); } catch (NoSuchMethodException | NoSuchFieldException | IllegalAccessException | InvocationTargetException e) { e.printStackTrace(); } } } 実行結果 x = 5
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

素の OpenJDK 8 だと maven のリポジトリからダウンロードに失敗するので対処した件

今更、OpenJDK 8 ですかというツッコミはなしで… Oracle JDK から OpenJDK に切り替えてから、maven のセントラルリポジトリから、以下のような警告が出てダウンロードができなくなりました。 [WARNING] Failed to retrieve plugin descriptor for org.apache.maven.plugins:maven-clean-plugin:2.5: Plugin org.apache.maven.plugins:maven-clean-plugin:2.5 or one of its dependencies could not be resolved: Failed to read artifact descriptor for org.apache.maven.plugins:maven-clean-plugin:jar:2.5 Downloading from central: https://repo.maven.apache.org/maven2/org/apache/maven/plugins/maven-install-plugin/2.4/maven-install-plugin-2.4.pom で、SSL の問題かと思い、 maven - MavenにSSLエラーを無視するように指示する方法(およびすべての証明書を信頼する方法) - ITツールウェブ というページを見つけ、以下のオプションを追加したら、ダウンロードできることは確認できました。 -Dmaven.wagon.http.ssl.insecure=true -Dmaven.wagon.http.ssl.allowall=true -Dmaven.wagon.http.ssl.ignore.validity.dates=true ですが、セキュリティを無視するわけですから、気持ちよくありません。 おそらく https://repo.maven.apache.org/ の証明書を発行している認証局のルート証明書(DigiCert Global Root CA)が OpenJDK のキーストアに入ってないのだろうということで Java環境に手動でグローバルサインのルート証明書をインストールする方法 | サポート・お申し込みガイド | GMOグローバルサイン【公式】 を参考に keytool を実行したのですが、キーストアの初期パスワードが分からないという罠に。 java - OpenJDK keytool password - Stack Overflow を見つけ、changeit であることが分かりました。 keytool -import -alias DigiCertGlobalRootCA -keystore Path\to\java-se-8u41-ri\jre\lib\security\cacerts -file filename.pem 無事にキーストアに追加でき、特にオプションを指定しなくても Maven セントラルリポジトリから、ダウンロードできるようになりました。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

ものづくりしながらJavaをマスターする 改訂版

やってみて・・・ 少し意味がわかったぐらい。あんまり深みにはまりすぎると問題なので・・・ 完了条件 改訂版がついてる場合 要旨 ものづくりしながらJavaをマスターする。 やること・やらないこと やらないこと Java8以降 業務の仕様 データベース関連 やること サーバー インプット サーバー リンク https://github.com/todokr/simple-http-server https://speakerdeck.com/todokr/xin-siihurokuraminkuyan-yu-falsexue-hifang-httpsahawozuo-tutexue-hu-java-scala-clojure https://nowokay.hatenablog.com/entry/20160419/1461032474 アウトプット ・一旦端から動かしてみる。 内容 目次 ・振り返り ・動きの確認 コード等 ・コードを動かす。 ・TakeAway 振り返り 動きの確認 事前準備 python3 -m http.server 通信の中身の確認 HTTP/1.0 200 OK Server: SimpleHTTP/0.6 Python/3.8.3 Date: Fri, 16 Apr 2021 02:43:07 GMT Content-type: text/html Content-Length: 1395 Last-Modified: Fri, 02 Apr 2021 03:28:36 GMT <!-- Copyright 2016 Google Inc. Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. limitations under the License. --> <!-- referenced in: https://developers.google.com/web/tools/chrome-devtools/javascript --> <!doctype html> <html> <head> <title>Demo: Circle Ten </title> <meta name="viewport" content="width=device-width, initial-scale=1"> <style> h1 { font-size: 1.5em } input, button { min-width: 72px; min-height: 36px; border: 1px solid grey; } label, input, button { display: block; } input { margin-bottom: 1em; } </style> </head> <body> <h1>Demo: Demo: Circle Ten</h1> <label for="num1">Number 1</label> <input placeholder="Number 1" id="num1"> <label for="num2">Number 2</label> <input placeholder="Number 2" id="num2"> <button>Number 1 + (Number 1 * 0.9) * Number 2 </button> <p></p> <script src="get-started.js"></script> </body> </html> 分析 SimpleJavaHttpServer.java ↓ Request.java ↓ RequestParser.java ↓ RequestHandler.java ↓ Response.java 分析 Server TakeAway 以下の記事は読み込んでおこうと思う。 Pathsについて https://www.baeldung.com/java-nio-2-path 名前付きグループについて https://qiita.com/jnchito/items/cceb669cb06fc044f411
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Webサーバーを作りながらJavaをマスターする 改訂版

やってみて・・・ 少し意味がわかったぐらい。あんまり深みにはまりすぎると問題なので・・・ TakeAway 以下の記事は読み込んでおこうと思う。 Pathsについて https://www.baeldung.com/java-nio-2-path 名前付きグループについて https://qiita.com/jnchito/items/cceb669cb06fc044f411 完了条件 改訂版がついてる場合 要旨 ものづくりしながらJavaをマスターする。 やること・やらないこと やらないこと Java8以降 業務の仕様 データベース関連 やること サーバー インプット サーバー リンク https://github.com/todokr/simple-http-server https://speakerdeck.com/todokr/xin-siihurokuraminkuyan-yu-falsexue-hifang-httpsahawozuo-tutexue-hu-java-scala-clojure https://nowokay.hatenablog.com/entry/20160419/1461032474 アウトプット ・一旦端から動かしてみる。 内容 目次 ・動きの確認 コード等 ・コードを動かす。 ・TakeAway 動きの確認 事前準備 python3 -m http.server 通信の中身の確認 HTTP/1.0 200 OK Server: SimpleHTTP/0.6 Python/3.8.3 Date: Fri, 16 Apr 2021 02:43:07 GMT Content-type: text/html Content-Length: 1395 Last-Modified: Fri, 02 Apr 2021 03:28:36 GMT <!-- Copyright 2016 Google Inc. Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. limitations under the License. --> <!-- referenced in: https://developers.google.com/web/tools/chrome-devtools/javascript --> <!doctype html> <html> <head> <title>Demo: Circle Ten </title> <meta name="viewport" content="width=device-width, initial-scale=1"> <style> h1 { font-size: 1.5em } input, button { min-width: 72px; min-height: 36px; border: 1px solid grey; } label, input, button { display: block; } input { margin-bottom: 1em; } </style> </head> <body> <h1>Demo: Demo: Circle Ten</h1> <label for="num1">Number 1</label> <input placeholder="Number 1" id="num1"> <label for="num2">Number 2</label> <input placeholder="Number 2" id="num2"> <button>Number 1 + (Number 1 * 0.9) * Number 2 </button> <p></p> <script src="get-started.js"></script> </body> </html> 分析 SimpleJavaHttpServer.java ↓ Request.java ↓ RequestParser.java ↓ RequestHandler.java ↓ Response.java 分析 Server
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む