ChatGPTと人工知能の倫理について議論してみた

ChatGPTと人工知能の倫理について議論してみました。ChatGPTの回答は抜け目がないというか、抽象的で当たり障りのない回答が多い印象を受けました。議論自体はできておもしろかったのですが、踏み込んだ回答はあまりできませんでした。ChatGPTにも具体的にこうしたらいいという案を示してもらえたら、やりやすかったのかなと思います。ChatGPTもプログラムの一種なので、おかしな回答がされないように裏側で制限をされているのでしょうか。

自分の知識の浅さを知らせるようで少し恥ずかしいですね(笑) ChatGPTの回答になるほどな~と感じるところもありました。ChatGPTと議論するのは思ったよりも大変でした。


何か議論しましょう

ChatGPT

もちろんです。何について議論したいですか? 政治、科学、文化、倫理、または他のトピックに関心がありますか?

なんでもいいです

ChatGPT

では、興味深いトピックの一つとして、人工知能の倫理について議論してみましょう。人工知能の進歩が加速し、その利用範囲が広がる中で、倫理的な問題が浮かび上がっています。例えば、個人のプライバシー、自律的なAIの安全性、差別や偏見の問題などが挙げられます。あなたはどのような観点からこの問題を見ますか?

AIは道具に過ぎないと考えます。その道具を使うのは人間なので、人間がまずは進化すべきと考えます。

ChatGPT

興味深い観点ですね。確かに、AIは現時点では道具であり、その使用や影響は人間がコントロールする必要があります。人間の進化や倫理的な発展が重要であるという視点は、技術が進歩するにつれてますます重要になります。

ただし、AIがより複雑なタスクや意思決定に関与するようになるにつれて、人間がAIの影響を完全に制御することが難しくなる可能性もあります。例えば、自律的なAIシステムが重要な意思決定を行う場合、その決定が倫理的かつ社会的に望ましい結果をもたらすように保証する必要があります。

そのため、AIの使用や開発には倫理的な枠組みや規制が必要であるという意見もあります。人間が進化し、技術に対処する能力を高めることも重要ですが、同時に技術の進歩に伴う倫理的な考慮も進化させる必要があるという見方もあります。

AI倫理については詳しくないのですが、何が人間社会にとって利益となるのかを定義しないといけないということですね。重要な意思決定は必ず人間が介在するようにするようにすればどうでしょうか。

ChatGPT

はい、そのようなアプローチは一般的に倫理的な観点から重要視されます。人間が重要な意思決定に介入し、AIシステムの活動や結果を監視し、必要に応じて修正することは、技術が人間の利益や価値に反する可能性を軽減する上で重要です。

また、AIシステムを設計する際には、倫理的な原則や社会的な価値を組み込むことが重要です。例えば、公平性、透明性、プライバシーの尊重などが挙げられます。これらの原則は、AIシステムが人間の社会に有益であることを確保する上で役立ちます。

さらに、重要な意思決定には人間の判断や倫理的な洞察が必要であるという観点から、AIシステムが支援的な役割を果たす場合でも、最終的な決定権を人間に委ねることが望ましいとされます。このようなアプローチは、技術が人間の価値観や倫理的な基準に合致するようにするための重要な手段となります。

AIの使用や開発には倫理的な枠組みや規制が必要であるという意見もあります。人間が進化し、技術に対処する能力を高めることも重要ですが、同時に技術の進歩に伴う倫理的な考慮も進化させる必要があるという見方もあります。

あなたは上の文章についてどう思いますか。

ChatGPT

上記の文章は非常に重要な観点を指摘しています。確かに、AIの使用や開発には倫理的な枠組みや規制が必要です。技術の進歩が速い現代社会では、倫理的な考慮が追いつかない場合があり、それが重大な問題を引き起こす可能性があります。例えば、プライバシーの侵害や差別的なアルゴリズムの使用などが挙げられます。

また、人間が進化し、技術に対処する能力を高めることも重要ですが、同時に倫理的な観点や考慮も進化させる必要があります。技術の進歩とともに、その技術が人間社会に与える影響や潜在的なリスクを理解し、それに対処するための適切な倫理的な枠組みを構築することが重要です。

つまり、技術と倫理は切り離せないものであり、両者をバランスよく考慮することが、持続可能な社会的発展に不可欠です。

倫理的な枠組みを作成するのは良い案だと思います。

AIがサイバー攻撃に利用される可能性についてはどう思いますか。

ChatGPT

AIがサイバー攻撃に利用される可能性は非常に現実的な懸念です。AIの能力を悪用して、より洗練された攻撃を実行することができます。例えば、AIを使用して不正な電子メールを作成し、フィッシング攻撃を行ったり、AIを使用してセキュリティシステムを乗り越えたりすることが考えられます。

このようなリスクを軽減するためには、倫理的な観点からだけでなく、技術的な対策も必要です。例えば、セキュリティ対策の強化やAIの利用に関する規制、監視などが考えられます。また、AIを悪用して行われる可能性のある攻撃に対処するための研究や対策の開発も重要です。

一方で、AI自体がサイバー攻撃を防ぐための有効なツールにもなり得ます。例えば、AIを使用して不審な行動やパターンを検出し、セキュリティシステムを強化することができます。しかし、このような利用も倫理的な考慮が必要であり、プライバシーや個人の権利を侵害しないように注意する必要があります。

難しい問題ですね

ChatGPT

はい、確かに難しい問題です。AIの進化が加速し、その利用範囲が広がるにつれて、新たな倫理的な問題や技術的なリスクが浮かび上がっています。このような問題に対処するためには、政府、産業界、学術界、市民社会などの幅広いステークホルダーが協力して、適切な枠組みや規制、技術的な対策を開発していく必要があります。

また、これらの問題に対処するためには、専門家や倫理的な観点に詳しい人々との議論や意見交換が重要です。さまざまな視点や経験を取り入れることで、より包括的な解決策を見出すことができるでしょう。 AIの進化とその影響に対処するために、長期的な取り組みと共同作業が必要です。

今のところAIが人間を超えるということに実感がありません。確かに知識では人間を上回っているようですが、現実世界に直接影響を与えるようなものになるとは思えません

ChatGPT

確かに、現在のAI技術は人間の知識や特定のタスクにおいて驚くほどの能力を示していますが、人間の複雑な判断や創造性、直感など、さまざまな側面でまだまだ及ばない部分があります。AIはあくまでプログラムやアルゴリズムに基づいて行動し、その行動は人間によって設計され、制御されています。

しかし、一部の専門家や研究者は、将来的にAIが人間を超える可能性について議論しています。例えば、超知能(superintelligence)と呼ばれる、人間の知能を大幅に超えたAIの開発が実現すれば、人間の理解や制御を超える可能性があります。このような未来の展望に対しては、慎重かつ倫理的なアプローチが求められます。

現時点では、AIが人間を超えるという直接の実感がないのは自然なことです。しかし、技術の進歩は予測困難な場合もありますので、適切な警戒心を持ちながら、AIの発展について関心を持ち続けることが重要です。

超知能というもののイメージがわかりませんが、AIは所詮AI、人間の事情は考慮できないと考えます。人間社会は想像以上に複雑です。

ChatGPT

確かに、人間社会は非常に複雑であり、AIがすべての人間の事情や文化的な背景を理解し、それらを適切に考慮することは難しいでしょう。AIはプログラムやデータに基づいて行動し、その範囲内でのみ活動します。人間の感情や道徳的な判断、文化的な違いなど、AIが理解しにくい要素が存在します。

超知能という概念は、人間の知能を大幅に超えたAIの開発に関する議論の中で登場する概念です。超知能AIは、あらゆる問題を解決し、人間の理解を超えるような能力を持つと想定されています。しかし、このような技術の実現はまだ未来の話であり、多くの不確定要素や議論が存在します。

【Python】Java Access Brigeで自動化

目標

Java Access Bridgeを利用してJavaアプリを自動化する。

背景

ブラウザやWindowsアプリはたいていの場合、SeleniumやUIAutomationを利用すれば自動化できる。しかし、Javaアプリの場合、Java実行環境を介して実行しているためか、エレメント情報を取得することができず自動化することが難しい。 そこで調査したところ、JavaAccessBridgeというものを利用すればJavaアプリを自動化できるそう。 検証してみる。

UIAutomationではJavaのエレメント取得ができない理由については別の記事にまとめる。

Java Access Bridgeとは何か

公式の説明を読み解いていく。

Microsoft Windows DLL で Java Accessibility API を公開するテクノロジで、Java Accessibility API を実装する Java アプリケーションおよびアプレットMicrosoft Windows システム上のユーザー補助テクノロジから可視にできます。

Javaアプリの情報を取得するためには、Javaに実装されているJava Accessibility APIというものを利用する必要がある。Java Access Bridge(以下、JAB)はそのAPIをDLLとして公開することでWindowsからJavaアプリのエレメント情報にアクセスする手段を提供するものである。JABの実態は、jdk/bin/windowsaccessbridge-64.dll, jdk/bin/javaaccessbridge.dllからなる。前者はWindowsとのやり取りを行うもの、後者はJavaアプリとのやり取りを行うものである。

Java Accessibility APIJava Accessibility ユーティリティー の一部で、Java Accessibility API を実装する GUI ツールキットへのアクセスをユーザー補助テクノロジが提供するのを支援するユーティリティークラスのセットです。

Java Accessibility APIJavaアプリのGUI(ボタンやテキスト、フォーム等)のエレメント情報やイベント情報を取得するAPIということ。ユーザ補助テクノロジというのはAccess Bridge Explorer(以下、ABE)のようにJavaアプリのエレメント情報をキャプチャできるツールのこと。ABEで取得したエレメント情報をもとにJavaアプリを操作することが可能となる。

Microsoft Windows 上で実行されているユーザー補助テクノロジアプリケーション (画面リーダーなど) は Java Access Bridge DLL とやり取りし、Java Access Bridge DLL は Java Access Bridge Java ライブラリ経由で Java Virtual Machine とやり取りします。これらの Java ライブラリは Java Accessibility ユーティリティーとやり取りします。Java Accessibility ユーティリティーJava アプリケーションで発生していることについての情報を収集し、それらは Java Access Bridge 経由で画面リーダーに転送されます。

どのようにJavaアプリから情報を取得しているかの説明。JAB DLLのはクラスライブラリであり、クラスを利用してJava Virtual Michine(Java Accessibility Utility)とやり取りしている。Java Accessibility Utilityこそが画面関連情報を取得している本体ということ。

JABは結果的にはJava Accessibility Utilityとやり取りして、Javaアプリの画面情報を取得している。

実際にPythonで書いてみる

ここではpyjabというライブラリを利用して、Android Studioを操作してみる。使用感はSeleniumと似ていて、driverオブジェクトのメソッドを利用して操作する。

環境、必要なもの

事前準備

Android Studioを起動して色々試してみる

README.mdのサンプルプログラムをベースに書いていく。前提条件として、jdk-21.0.1\bin\windowsaccessbridge-64.dllをワーキングディレクトリに配置しておく必要がある。

import pyjab.jabdriver
import pathlib

# Point 1. Create a JABDriver object.
jabdriver = pyjab.jabdriver.JABDriver(title='My Application', file_path=pathlib.Path(r'C:\Program Files\Android\Android Studio\bin\studio64.exe'))

# Point 2. Find a JABElement by element name
element = jabdriver.find_element_by_name("Resource Manager")

# Point 3. Click a JABElement
element.click()

# Point 4. Get property of JABElement
name = element.name
description = element.description
role = element.role
role_en_us = element.role_en_us
states = element.states
states_en_us = element.states_en_us
object_depth = element.object_depth
index_in_parent = element.index_in_parent
children_count = element.children_count
# Return {x, y, height, width}
bounds = element.bounds
accessible_component = element.accessible_component
accessible_action = element.accessible_action
accessible_selection = element.accessible_selection
accessible_text = element.accessible_text
text = element.text
table = element.table

Point 1ではJavaアプリ操作のためのJabdriverを作成している。Jabdriverの作成はJabを起動することと同じ意味。既に起動しているJavaアプリのjabdriverを作成する方法もあれば、Javaアプリを起動後jabdriverを作成する方法もある。ケースバイケースで使い分けるとよい。注意点は、titleに指定するウィンドウ名がGUIの表示されているものウィンドウ名と異なる場合がある。no java window found by title 'My Application' in '30'secondsのようなエラーが出る場合は、win32等で取得したウィンドウ名を確認してみるとよい。

Point 2では操作対象のエレメントを取得している。ここではname属性で指定している。ほかにも

  • description
  • role
  • states
  • object depth
  • children count
  • index in parent
  • xpath

の属性から検索することが可能。また、サンプルプログラムは最初にヒットしたエレメントを取得するメソッドを使用しているが、find_elements_by_nameのようにヒットしたすべてのエレメントを取得するメソッドも存在する。個人的な感覚だが、name, role, object depthあたりが有用だと思う。xpathが取得できればよいが、その方法は調査中。

Point 3ではエレメントへのクリック命令の送信やエレメント情報を取得している。エレメントによっては送信できる命令や取得できる情報が異なるので注意。AccessibleAction supportedが有効なエレメントはクリック操作が可能だったり、AccessibleSelection supportedが有効なエレメントは選択操作が可能だったり、AccessibleText supportedが有効なエレメントは表示テキストの取得が可能だったりする。

JAB APIのドキュメントをみてみる

Java Access Bridge APIのドキュメントを確認してみる。Java Access Bridgeを利用するフローは、

  1. JABを起動(initializeAccessBridge関数)
  2. JavaアプリのAccessibility API実装の有無を確認(IsJavaWindow関数)
  3. JAB APIのベースとなるアプリ情報を取得(GetAccessibleContextFromHWND関数)
  4. JAB APIJavaアプリを操作(各種Accessible関数)
  5. JABを終了(shutdownAccessBridge関数)

となる。1-3は上記プログラムのPoint 1でまとめて行っている。JABDriverのInit関数はvenv\Lib\site-packages\pyjab\jabdriver.pyに記載があるので確認してみるとよい。4はPoint 2-4で行っている。エレメントのデータ構造はAPIデータ構造に記載されているので、どのような情報を取得できるのか確認するとよい。個人的には、AccessibleContextInfo, AccessibleTextInfoのデータの使用頻度が高い。

参考

ユーザー補助テクノロジ開発者向け Java Access Bridge プログラマーズガイド

pyjab

【Java Access Bridge】Access Bridge Explorerでエレメント情報を取得する

目標

Access bridge ExplorerJavaアプリの要素データを取得すること

背景

Javaアプリを自動化するため、Javaアプリのエレメント情報を取得したかった

環境

Windows 10

1. OpenJDKのダウンロード

OpenJDKをダウンロード。 解凍し、任意のフォルダに移動。

2. システム環境変数の設定

jdk/binにパスを通す。 cmdでjavaが打てればOK

3. Java Access Bridgeの有効化

cmdで下記を実行。

$ jabswitch -enable
The Java Access Bridge has been enabled.

4. Access Bridge Explorerのダウンロード

Access Bridge Explorerをダウンロード。 AccessBridgeExplorer.exeを実行。 Accessibility TreeにJavaアプリが表示されていればOK。

5. (オプション)Android Studioのインストール

Javaアプリが手元にない場合、Android Studioで検証してみる。 Android StudioJavaアプリである。 起動後、Accessibility TreeにJavaアプリが表示されていればOK。

参考

https://github.com/google/access-bridge-explorer

【Nginx】Flask,Gunicornアプリをプロキシする

Run Flask app and Gunicorn

flask --app run_server run --debug --host=0.0.0.0 --port=80
gunicorn -w 4 run_server:app -b 0.0.0.0:8080 --reload --access-logfile /var/log/gunicorn/access.log --error-logfile /var/log/gunicorn/error.log --capture-output

For SSL.

gunicorn -w 4 run_server:app -b 0.0.0.0:8080 --reload --access-logfile /var/log/gunicorn/access.log --error-logfile /var/log/gunicorn/error.log --capture-output  --keyfile cert/server.key --certfile cert/server.crt

Combined Nginx and Gunicorn.

/etc/nginx/nginx.conf
/etc/systemd/systemd/gunicorn.service
/etc/systemd/systemd/gunicorn.socket

HTTP request to socket in Almalinux

sudo -u nginx curl --unix-socket /run/gunicorn.sock http

[NOTE]Should restart gunicorn service when modify flask app.

systemctl restart gunicorn.socket

Reference

http://nginx.org/en/docs/beginners_guide.html https://docs.gunicorn.org/en/latest/deploy.html Unix Domain Socket

https://www.freedesktop.org/software/systemd/man/systemd.service.html#Type= https://www.freedesktop.org/software/systemd/man/systemd.unit.html

Nginx Reverse Proxy Hello World

http {
    server {
        port 80;
        root /usr/share/nginx/html;
        
        location / {
            # return index.html in directroy.
            proxy_pass http://app_server;
        }
        
    }
}

/etc/nginx/nginx.conf

# For more information on configuration, see:
#   * Official English Documentation: http://nginx.org/en/docs/
#   * Official Russian Documentation: http://nginx.org/ru/docs/

user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log;
pid /var/run/nginx.pid;

# Load dynamic modules. See /usr/share/doc/nginx/README.dynamic.
include /usr/share/nginx/modules/*.conf;

events {
    worker_connections 1024;
    accept_mutex off; # set to 'on' if nginx worker_processes > 1
}

http {
    log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';

    access_log  /var/log/nginx/access.log  main;

    tcp_nopush          on;
    tcp_nodelay         on;
    keepalive_timeout   65;
    types_hash_max_size 2048;

    include             /etc/nginx/mime.types;
    default_type        application/octet-stream;
    sendfile            on;

    # Load modular configuration files from the /etc/nginx/conf.d directory.
    # See http://nginx.org/en/docs/ngx_core_module.html#include
    # for more information.
    include /etc/nginx/conf.d/*.conf;

    upstream app_server {
        # server unix:/tmp/gunicorn.sock fail_timeout=0;
        server unix:/run/gunicorn.sock fail_timeout=0;
    }

    # server {
    #     listen       80 default_server;
    #     listen       [::]:80 default_server;
    #     server_name  _;
    #     root         /usr/share/nginx/html;

    #     # Load configuration files for the default server block.
    #     include /etc/nginx/default.d/*.conf;

    #     location / {
    #     }

    #     error_page 404 /404.html;
    #         location = /40x.html {
    #     }

    #     error_page 500 502 503 504 /50x.html;
    #         location = /50x.html {
    #     }
    # }

    # server {
    #     listen 80;
    #     client_max_body_size 4G;
    #     # server_name example.com www.example.com;
    #     
    #     keepalive_timeout 5;

    #     location / {
    #         try_files $uri @proxy_to_app;
    #     }

    #     location @proxy_to_app {
    #         proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    #           proxy_set_header X-Forwarded-Proto $scheme;
    #         proxy_set_header Host $http_host;
    #         # we don't want nginx trying to do something clever with
    #         # redirects, we set the Host: header above already.
    #         proxy_redirect off;
    #         proxy_pass http://app_server;
    #     }

    #     error_page 500 502 503 504 /500.html;
    #     location = /500.html {
    #         
    #     }
    # }
    server {
        listen    80;
        # server_name 127.0.0.1;
        client_max_body_size 4G; # Default: 1MB.

        keepalive_timeout 5;

        # static file path
        root /usr/share/nginx/html;

        location / {
            # checks for static file, if not found proxy to app
            try_files $uri @proxy_to_app;
        }

        location @proxy_to_app {
            # Add header information to pass to Flask app.
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;
            proxy_set_header Host $http_host;
                # we don't want nginx trying to do something clever with
            # redirects, we set the Host: header above already.
            proxy_redirect off;
            proxy_pass http://app_server;
        }
    }
    server {
        listen 8888;
        location / {
            proxy_pass http://localhost:8889;
            # root /usr/share/nginx/www2/html;
        }
        location ~ \.(gif|jpg|png)$ {
            root /usr/share/nginx/www2/images;
        }
    }
    server {
        listen 8889;
        root /usr/share/nginx/www2/up1;
        location / {

        }
    }

# Settings for a TLS enabled server.
#
#    server {
#        listen       443 ssl http2 default_server;
#        listen       [::]:443 ssl http2 default_server;
#        server_name  _;
#        root         /usr/share/nginx/html;
#
#        ssl_certificate "/etc/pki/nginx/server.crt";
#        ssl_certificate_key "/etc/pki/nginx/private/server.key";
#        ssl_session_cache shared:SSL:1m;
#        ssl_session_timeout  10m;
#        ssl_ciphers PROFILE=SYSTEM;
#        ssl_prefer_server_ciphers on;
#
#        # Load configuration files for the default server block.
#        include /etc/nginx/default.d/*.conf;
#
#        location / {
#        }
#
#        error_page 404 /404.html;
#            location = /40x.html {
#        }
#
#        error_page 500 502 503 504 /50x.html;
#            location = /50x.html {
#        }
#    }

}

/etc/systemd/system/gunicorn.service

[Unit]
Description=gunicorn daemon
Requires=gunicorn.socket
After=network.target

[Service]
Type=notify
User=almalinux
Group=almalinux

# Generate "gunicorn" folder in "/run/" directory. Delete when stoped.
RuntimeDirectory=gunicorn
# Generate "gunicorn" folder in "/var/log/" directory.
LogsDirectory=gunicorn
# Generate "gunicorn" folder in "/etc/" directory.
ConfigurationDirectory=gunicorn

WorkingDirectory=/home/almalinux/helloworld/gunicorn
ExecStart=/home/almalinux/helloworld/gunicorn/venv/bin/gunicorn -w 4 run_server:app -b 0.0.0.0:8080 --reload --access-logfile /var/log/gunicorn/access.log --error-logfile /var/log/gunicorn/error.log --capture-output
ExecReload=/bin/kill -s HUP $MAINPID
KillMode=mixed
TimeoutStopSec=5
PrivateTmp=5

[Install]
WantedBy=multi-user.target

/etc/systemd/system/gunicorn.sock

[Unit]
Description=gunicorn socket

[Socket]
ListenStream=/run/gunicorn.sock
# Our service won't need permissions for the socket, since it
# inherits the file descriptor by socket activation
# only the nginx daemon will need access to the socket
SocketUser=nginx
# Optionally restrict the socket permissions even more.
# SocketMode=600

[Install]
WantedBy=sockets.target

【Switch】L3 Switch(Router)とL2 Switchについて

ネットワーク初心者のため、参考にする際は誤情報があることがありますので注意してください。 備忘録の記事になります。

まずはPortについてざっくり。

L2スイッチ

L3スイッチ

つまり、Routed Portが1つ以上あれば(=異なるネットワークを結ぶことができれば)L3スイッチになる。

インターネット環境構成図

ルータ=L3スイッチと思っていたが違う様子。また今後、調査する。

【Linux】構築時の初期設定メモ

Linuxサーバ(CentOS, Almalinux)構築後に行う設定作業をメモしておく。

yum update -y

# Sudo can be used no password. (Just Intranet.)
visudo
visudo -c

# Create User
useradd <username>
passwd <username>

# Give sudo Authority to created user
usermod -aG wheel almalinux

# Install software packages
tar # For VS Code.
tmux
git
wget
vim
python (miniconda, pyenvy or From AppStream)

# SELinux is disabled. (Just Intranet.)
vim selinux # Disabled

# Auto log.
mkdir ~/logs
vim ~/.bash_profile に script ~/logs/$(date +%Y%m%d_%H%M%S).log を追記

# Enable access with key authentication.
mkdir .ssh
chmod 700 ~/.ssh
vim ~/.ssh/authorized_keys # Register private key of LOCAL
chmod 600 ~/.ssh/authorized_keys

# Disable firewall. (Just Intranet.)
sudo systemctl stop firewalld
sudo systemctl disable firewalld

# Setting static IP.
sudo yum install net-tools
route # Check default gateway
cat /etc/resolve.conf # Check DNS IPadress
sudo nmcli connection modify <NIC> ipv4.addresses "192.168.x.x/24"
sudo nmcli connection modify <NIC> ipv4.gateway 192.168.x.0
sudo nmcli connection modify <NIC> ipv4.dns 192.168.x.0
sudo nmcli connection modify <NIC> ipv4.method manual
sudo nmcli connection down <NIC>
sudo nmcli connection up <NIC>