9
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

UNIQLO Akamai Tシャツコード - Goによる平行処理 -

Last updated at Posted at 2023-04-24

概要

ユニクロがAkamaiというインターネット企業とコラボしてTシャツをデザインしました。

Tシャツのデザインは、Go言語のプログラムをモチーフにしています。
しかし、それはそのプログラムは、Go言語の一部が欠落しているプログラムでした。

そこで、AIの力を借りて、足りない部分を補って、動くコードとして復元しました。

すると、ミニナムなサーバープログラムが復元されました。

以下に、復元方法と、プログラムの簡単な説明をしていきたいと思います。

T-Shirt_View

復元手順

まず、Tシャツのコードを、パソコンに読み込む必要があります。

そこで、スマホでTシャツの写真を撮って、スマホの写真から文字を抽出する機能を使って、プログラムをテキスト化しました。

ちなみに、これも文字を認識する画像認識AIの一種です。

次に、自力でコードを組み立てようとしましたが、これは一部に欠損のあるプログラムであることが分かりました。

そこで、ChatGPTに、画像から抽出した文字列を、プログラムとして復元するように依頼しました。

すると、ほぼ完全な状態でChatGPTがコードを、動く状態で復元してくれました。

ここで初めて、私がどのように動くのかということを解析して、これは簡易的なサーバープログラムであることが分かりました。

また、Go言語のプログラムらしく、ゴルーチンを用いた平行処理も取り入れられていて、サーバーに処理をリクエストすると平行的に処理してくれることも判明しました。

Code_View

コード

func main() {
	controlChannel := make(chan ControlMessage)
	workerCompleteChan := make(chan bool)
	pollChannel := make(chan chan bool)
	workerActive := false

	go func() {
		for {
			select {
			case respChan := <-pollChannel:
				respChan <- workerActive
			case msg := <-controlChannel:
				workerActive = true
				go doStuff(msg, workerCompleteChan)
			case status := <-workerCompleteChan:
				workerActive = status
			}
		}
	}()

	http.HandleFunc("/admin", func(w http.ResponseWriter, r *http.Request) {
		r.ParseForm()
		count, err := strconv.ParseInt(r.FormValue("count"), 10, 32)
		if err != nil {
			log.Printf("Error parsing count: %v", err)
			return
		}
		msg := ControlMessage{
			Target: r.FormValue("target"),
			Count:  int(count),
		}
		controlChannel <- msg
		fmt.Fprintf(w, "Control message issued for Target %s\n", html.EscapeString(r.FormValue("target")))
	})

	http.HandleFunc("/status", func(w http.ResponseWriter, r *http.Request) {
		reqChan := make(chan bool)
		pollChannel <- reqChan
		timeout := time.NewTimer(5 * time.Second)
		select {
		case result := <-reqChan:
			if result {
				fmt.Fprintln(w, "ACTIVE")
			} else {
				fmt.Fprintln(w, "INACTIVE")
			}
		case <-timeout.C:
			fmt.Fprintln(w, "TIMEOUT")
		}
	})

	log.Fatal(http.ListenAndServe(":8080", nil))
}

プログラムの実行

次は実行方法です。図を用いて動かし方を紹介します。

まず、左側のコンソールでプログラムを起動し、簡易的なサーバーとして見立てます。
次に、右側のコンソールを起動し、サーバーにリクエストする準備をします。

試しに、起動しただけの状態でステータスリクエストを行うと、'INACTIVE'が応答されます。
そして、POSTで処理をリクエストした後に、ステータスリクエストを行うと、'ACTIVE'が応答されます。

処理リクエストは、ゴルーチンらしく複数受け付けられます。
複数処理をリクエストすると、サーバー側の処理が加速していくのが確認出来るはずです。

コマンド Memo

サーバー側

~ $ go build -o Akamai Akamai.go
~ $ ./Akamai
Target: Akamai T-Shirt A , Count: 0
Target: Akamai T-Shirt A , Count: 1
Target: Akamai T-Shirt A , Count: 2
Target: Akamai T-Shirt A , Count: 3
Target: Akamai T-Shirt B , Count: 0
Target: Akamai T-Shirt A , Count: 4
Target: Akamai T-Shirt B , Count: 1

クライアント側

~ $ curl http://localhost:8080/status
INACTIVE
~ $ curl -X POST -d "target=Akamai T-Shirt A &count=30" http://localhost:8080/admin
Control message issued for Target Akamai T-Shirt A
~ $ curl -X POST -d "target=Akamai T-Shirt B &count=30" http://localhost:8080/admin
Control message issued for Target Akamai T-Shirt B
~ $ curl -X POST -d "target=Akamai T-Shirt C &count=30" http://localhost:8080/admin
Control message issued for Target Akamai T-Shirt C
~ $ curl http://localhost:8080/status
ACTIVE

GitHub

Twitter

9
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
9
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?