Tôi đang tạo một ứng dụng PySpark 3.4.1 để phát triển trong docker với Python 3.11.5, Ứng dụng này có thể kết nối với nhiều loại cơ sở dữ liệu thông qua kết nối JDBC. Tôi đang kiểm tra kết nối với Oracle DB cục bộ mà tôi thiết lập bằng docker trong một container khác. Tuy nhiên, tôi nhận được lỗi sau:
Tôi đang tạo một ứng dụng PySpark 3.4.1 được phát triển cùng với Python 3.11.5, ứng dụng này có thể kết nối với nhiều loại cơ sở dữ liệu thông qua kết nối JDBC. Tôi đang kiểm tra kết nối tới cơ sở dữ liệu Oracle cục bộ mà tôi đã thiết lập bằng docker trong một vùng chứa khác. Tuy nhiên, tôi nhận được lỗi sau:
Py4JJavaError: Đã xảy ra lỗi khi gọi o316.load.
: java.sql.SQLException: ORA-12541: Không thể kết nối. Không có trình lắng nghe tại máy chủ 127.0.0.1 cổng 1521. (CONNECTION_ID=ZHRvV1iVRICqrdGeoIq7BQ==)
Khi tôi chạy (sử dụng jar: "ojdbc11.jar"):
Khi tôi chạy (sử dụng JAR: "ojdbc11.jar"):
kết nối_opts = {
"trình điều khiển": "oracle.jdbc.driver.OracleDriver",
"url": "jdbc:oracle:thin:@127.0.0.1:1521/FREEPDB1",
"dbtable": "chọn * từ xtable",
"người dùng": "my_db_admin",
"mật khẩu": "20pwd23",
}
df = spark.read.format("jdbc").tùy chọn(**connection_opts).load()
Tệp docker-compose.yml như sau:
Tệp Docker-compose.yml trông như thế này:
phiên bản: "3.3"
dịch vụ:
spark-master:
hình ảnh: my_pyspark_image:latest
tty: đúng
stdin_open: đúng
cổng:
- "9090:8080"
- "7077:7077"
oracle-localdb:
# Tham khảo về việc tạo: https://hub.docker.com/r/gvenzl/oracle-free
hình ảnh: gvenzl/oracle-free:slim
Kích thước shm: 1g
cổng:
- '1521:1521'
môi trường:
ORACLE_RANDOM_PASSWORD: đúng
APP_USER: my_db_admin
MẬT KHẨU NGƯỜI DÙNG ỨNG DỤNG: 20pwd23
khối lượng:
- loại: khối lượng
nguồn: pyspark_oracle-volume
mục tiêu:/opt/oracle/oradata
khối lượng:
pyspark_oracle-khối lượng:
# bên ngoài: đúng
Khi tôi chạy trạng thái lsnrctl
:
Khi tôi chạy trạng thái lsnrctl:
LSNRCTL cho Linux: Phiên bản 23.0.0.0.0 - Bản phát hành dành cho nhà phát triển vào ngày 09-09-2023 18:49:38
Bản quyền (c) 1991, 2023, Oracle. Bảo lưu mọi quyền.
Đang kết nối tới (DESCRIPTION=(ADDRESS=(PROTOCOL=IPC)(KEY=EXTPROC_FOR_FREE)))
TRẠNG THÁI CỦA NGƯỜI NGHE
------------------------
Biệt danh LISTENER
Phiên bản TNSLSNR cho Linux: Phiên bản 23.0.0.0.0 - Phiên bản dành cho nhà phát triển
Ngày bắt đầu 09-09-2023 18:47:38
Thời gian hoạt động 0 ngày 0 giờ 1 phút 59 giây
Tắt mức theo dõi
Bảo mật BẬT: Xác thực hệ điều hành cục bộ
SNMP TẮT
Dịch vụ mặc định MIỄN PHÍ
Tệp tham số của trình nghe /opt/oracle/product/23c/dbhomeFree/network/admin/listener.ora
Tệp Nhật ký Người nghe /opt/oracle/diag/tnslsnr/6b3c2441425c/listener/alert/log.xml
Tóm tắt điểm cuối khi nghe...
(MÔ TẢ=(ĐỊA CHỈ=(GIAO THỨC=ipc)(KHÓA=EXTPROC_FOR_FREE)))
(MÔ TẢ=(ĐỊA CHỈ=(GIAO THỨC=tcp)(HOST=0.0.0.0)(PORT=1521)))
Tóm tắt dịch vụ...
Dịch vụ "MIỄN PHÍ" có 1 trường hợp.
Phiên bản "MIỄN PHÍ", trạng thái SẴN SÀNG, có 1 trình xử lý cho dịch vụ này...
Dịch vụ "FREEXDB" có 1 phiên bản.
Phiên bản "MIỄN PHÍ", trạng thái SẴN SÀNG, có 0 trình xử lý cho dịch vụ này...
Dịch vụ "fb99f7d127aa0bafe0536402000a43b5" có 1 phiên bản.
Phiên bản "MIỄN PHÍ", trạng thái SẴN SÀNG, có 1 trình xử lý cho dịch vụ này...
Dịch vụ "freepdb1" có 1 phiên bản.
Phiên bản "MIỄN PHÍ", trạng thái SẴN SÀNG, có 1 trình xử lý cho dịch vụ này...
Lệnh đã hoàn thành thành công
Người nghe.ora:
Người nghe.ora:
NGƯỜI NGHE =
(DANH SÁCH_MÔ TẢ =
(MÔ TẢ =
(ĐỊA CHỈ = (GIAO THỨC = IPC)(KHÓA = EXTPROC_FOR_FREE))
(ĐỊA CHỈ = (GIAO THỨC = TCP)(HOST = 0.0.0.0)(PORT = 1521))
)
)
DEFAULT_SERVICE_LISTENER = MIỄN PHÍ
Tnsnames.ora:
Tnsnames.ora:
MIỄN PHÍ =
(MÔ TẢ =
(ĐỊA CHỈ = (GIAO THỨC = TCP)(HOST = 0.0.0.0)(PORT = 1521))
(KẾT NỐI_DỮ LIỆU =
(SERVER = DEDICATED)
(SERVICE_NAME = MIỄN PHÍ)
)
)
FREEPDB1 =
(MÔ TẢ =
(ĐỊA CHỈ = (GIAO THỨC = TCP)(HOST = 0.0.0.0)(PORT = 1521))
(KẾT NỐI_DỮ LIỆU =
(SERVER = DEDICATED)
(TÊN_DỊCH_VỤ = FREEPDB1)
)
)
EXTPROC_CONNECTION_DATA =
(MÔ TẢ =
(DANH SÁCH ĐỊA CHỈ =
(ĐỊA CHỈ = (GIAO THỨC = IPC)(KHÓA = EXTPROC_FOR_FREE))
)
(KẾT NỐI_DỮ LIỆU =
(SID = PLSextProc)
(TRÌNH BÀY = RO)
)
)
Tôi đã thử kết nối tương tự với các cơ sở dữ liệu tùy chỉnh khác và với người dùng sys. Ngoài ra, tôi đã thử tạo container với nhiều cổng nhưng không thành công. Cuối cùng, tôi không biết điều này có giúp ích không nhưng tôi đã thử cái này và cũng chẳng có may mắn nào cả.
Tôi đã thử kết nối tương tự với các cơ sở dữ liệu và người dùng hệ thống được tạo tùy chỉnh khác. Ngoài ra, tôi đã thử tạo một vùng chứa có nhiều cổng nhưng không thành công. Cuối cùng, tôi không biết liệu điều này có giúp ích gì không, nhưng tôi cũng đã thử cách này nhưng không thành công.
Tôi đã thử kết nối với thư viện python oracledb:
Tôi cố gắng thiết lập kết nối với thư viện oracledb python:
nhập oracledb
kết nối = oracledb.connect(người dùng="my_db_admin", mật khẩu='20pwd23',
máy chủ="127.0.0.1", cổng=1521, tên_dịch_vụ="freepdb1")
Nhưng tôi hiểu thế này:
Nhưng tôi hiểu:
OperationalError: DPY-6005: không thể kết nối với cơ sở dữ liệu (CONNECTION_ID=M88go017TW5iuuV35FqWhw==).
[Errno 111] Kết nối bị từ chối
Có ai có thể giải thích cho tôi biết tôi đang thiếu gì không, cách giải quyết và nếu có thể thì làm sao để hiểu rõ hơn về các tệp .ora?
Bất cứ ai có thể giải thích cho tôi những gì tôi đang thiếu, cách khắc phục và nếu có thể, làm cách nào để hiểu rõ hơn về tệp .ora
Thêm câu trả lời
Tôi muốn bắt đầu bằng một câu hỏi:
Tôi muốn bắt đầu bằng một câu hỏi:
Bạn có đang chạy cơ sở dữ liệu Oracle trong vùng chứa 'spark-master' không?
Bạn có đang chạy cơ sở dữ liệu Oracle trong vùng chứa "Spark Master" của mình không?
Bởi vì, đó là cách bạn đã cấu hình kết nối cơ sở dữ liệu của mình bằng cách chỉ định máy chủ cục bộ/127.0.0.1
Bởi vì, đây là cách bạn định cấu hình kết nối cơ sở dữ liệu bằng cách chỉ định localhost/127.0.0.1
máy chủ cục bộ
là cục bộ đối với container. Không có cơ sở dữ liệu nào đang chạy trong container 'spark-master' của bạn. Nó đang chạy như một dịch vụ/container cùng với container 'spark-master' của bạn. Khi sử dụng docker compose, khám phá dịch vụ đang diễn ra ở chế độ ẩn và bạn có thể truy cập chúng theo tên.
Để liên hệ với dịch vụ cơ sở dữ liệu Oracle, bạn cung cấp tên oracle-localdb
localhost là cục bộ của vùng chứa. Không có cơ sở dữ liệu nào đang chạy trong vùng chứa 'spark-master' của bạn. Nó chạy như một dịch vụ/vùng chứa cùng với vùng chứa "spark-master" của bạn. Khi sử dụng Docker soạn thảo, việc khám phá dịch vụ diễn ra ở hậu trường và bạn có thể truy cập chúng theo tên. Để liên hệ với Dịch vụ cơ sở dữ liệu Oracle, vui lòng cung cấp tên oracle-localdb
Bây giờ, điều này sẽ có hiệu quả với bạn:
Bây giờ, điều này sẽ phù hợp với bạn:
nhập oracledb
kết nối = oracledb.connect(người dùng="my_db_admin", mật khẩu='20pwd23',
máy chủ="oracle-localdb", cổng=1521, tên_dịch_vụ="freepdb1")
Chúc bạn may mắn!
Chúc may mắn!
Thêm câu trả lời
Đây thực sự là một khám phá mới đối với tôi, tôi sẽ phải xem lại hiểu biết của mình về docker. Cảm ơn bạn rất nhiều.
Đây là một khám phá lớn đối với tôi và tôi sẽ phải xem xét lại sự hiểu biết của mình về Doc. Cảm ơn bạn rất nhiều.
Lưu ý rằng câu trả lời sử dụng trình điều khiển python-oracledb tương thích với API Python DB của Oracle có API khác với JDBC và chuỗi kết nối có thể là hơi khác một chút. Nhưng quan điểm chính của câu trả lời về việc sử dụng tên máy chủ chính xác vẫn đúng.
Lưu ý rằng câu trả lời là sử dụng trình điều khiển python-oracledb tương thích với API Python DB của Oracle, có API khác với JDBC và có thể có các chuỗi kết nối hơi khác. Tuy nhiên, điểm chính về việc sử dụng tên máy chủ chính xác vẫn đúng.
Tôi là một lập trình viên xuất sắc, rất giỏi!