couchbase 3.8.2 → 3.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (473) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +1 -1
  3. data/ext/CMakeLists.txt +16 -1
  4. data/ext/cache/cpm/{CPM_0.42.0.cmake → CPM_0.43.1.cmake} +18 -2
  5. data/ext/cache/extconf_include.rb +6 -6
  6. data/ext/cache/mozilla-ca-bundle.crt +121 -55
  7. data/ext/cache/mozilla-ca-bundle.sha256 +1 -1
  8. data/ext/couchbase/CMakeLists.txt +130 -21
  9. data/ext/couchbase/cmake/APKBUILD.in +25 -4
  10. data/ext/couchbase/cmake/Bundler.cmake +143 -34
  11. data/ext/couchbase/cmake/CPM.cmake +126 -12
  12. data/ext/couchbase/cmake/Cache.cmake +7 -1
  13. data/ext/couchbase/cmake/CompilerOptions.cmake +1 -1
  14. data/ext/couchbase/cmake/CompilerWarnings.cmake +17 -6
  15. data/ext/couchbase/cmake/GrpcProtobuf.cmake +481 -0
  16. data/ext/couchbase/cmake/OpenSSL.cmake +10 -3
  17. data/ext/couchbase/cmake/Packaging.cmake +519 -65
  18. data/ext/couchbase/cmake/Protostellar.cmake +250 -0
  19. data/ext/couchbase/cmake/Sanitizers.cmake +61 -50
  20. data/ext/couchbase/cmake/StaticAnalyzers.cmake +16 -5
  21. data/ext/couchbase/cmake/TestFramework.cmake +283 -0
  22. data/ext/couchbase/cmake/TestFrameworkAddTests.cmake +51 -0
  23. data/ext/couchbase/cmake/Testing.cmake +27 -9
  24. data/ext/couchbase/cmake/ThirdPartyDependencies.cmake +141 -8
  25. data/ext/couchbase/cmake/VersionInfo.cmake +50 -0
  26. data/ext/couchbase/cmake/build_config.hxx.in +2 -1
  27. data/ext/couchbase/cmake/couchbase-cxx-client.spec.in +101 -23
  28. data/ext/couchbase/cmake/couchbase_cxx_client_static-config.cmake.in +7 -0
  29. data/ext/couchbase/cmake/couchbase_cxx_client_static.pc.in +2 -0
  30. data/ext/couchbase/cmake/gRPC_Generate.cmake +58 -0
  31. data/ext/couchbase/cmake/protobuf_Generate.cmake +69 -0
  32. data/ext/couchbase/cmake/require-git-checkout.cmake +25 -0
  33. data/ext/couchbase/cmake/tarball_glob.txt +49 -0
  34. data/ext/couchbase/core/agent_group.cxx +0 -8
  35. data/ext/couchbase/core/agent_group.hxx +0 -4
  36. data/ext/couchbase/core/analytics_stream.cxx +314 -0
  37. data/ext/couchbase/core/analytics_stream.hxx +129 -0
  38. data/ext/couchbase/core/analytics_stream_component.cxx +245 -0
  39. data/ext/couchbase/core/analytics_stream_component.hxx +67 -0
  40. data/ext/couchbase/core/app_telemetry_meter.cxx +25 -3
  41. data/ext/couchbase/core/app_telemetry_meter.hxx +77 -0
  42. data/ext/couchbase/core/app_telemetry_reporter.cxx +7 -6
  43. data/ext/couchbase/core/bucket.cxx +381 -87
  44. data/ext/couchbase/core/bucket.hxx +105 -25
  45. data/ext/couchbase/core/bucket_unit_test_api.hxx +57 -0
  46. data/ext/couchbase/core/capella.hxx +91 -0
  47. data/ext/couchbase/core/cluster.cxx +1554 -398
  48. data/ext/couchbase/core/cluster.hxx +39 -8
  49. data/ext/couchbase/core/cluster_agent.cxx +0 -8
  50. data/ext/couchbase/core/cluster_agent.hxx +0 -4
  51. data/ext/couchbase/core/cluster_options.hxx +26 -3
  52. data/ext/couchbase/core/collections_component.cxx +39 -15
  53. data/ext/couchbase/core/config_profiles.cxx +1 -1
  54. data/ext/couchbase/core/crud_component.cxx +2 -2
  55. data/ext/couchbase/core/crud_options.hxx +34 -0
  56. data/ext/couchbase/core/crypto/cbcrypto.cc +18 -13
  57. data/ext/couchbase/core/document_id_redaction.hxx +81 -0
  58. data/ext/couchbase/core/error_context/base_error_context.hxx +7 -6
  59. data/ext/couchbase/core/error_context/key_value.cxx +25 -2
  60. data/ext/couchbase/core/error_context/key_value.hxx +60 -33
  61. data/ext/couchbase/core/error_context/key_value_error_context.hxx +16 -15
  62. data/ext/couchbase/core/error_context/search.hxx +5 -0
  63. data/ext/couchbase/core/error_context/search_json.hxx +3 -0
  64. data/ext/couchbase/core/error_context/subdocument_error_context.hxx +19 -18
  65. data/ext/couchbase/core/error_context/view.hxx +5 -0
  66. data/ext/couchbase/core/free_form_http_request.cxx +237 -4
  67. data/ext/couchbase/core/free_form_http_request.hxx +41 -8
  68. data/ext/couchbase/core/http_component.cxx +300 -284
  69. data/ext/couchbase/core/http_component.hxx +0 -4
  70. data/ext/couchbase/core/impl/analytics.cxx +38 -5
  71. data/ext/couchbase/core/impl/analytics.hxx +34 -0
  72. data/ext/couchbase/core/impl/bootstrap_error.hxx +0 -3
  73. data/ext/couchbase/core/impl/collection.cxx +215 -202
  74. data/ext/couchbase/core/impl/collection_manager.cxx +1 -1
  75. data/ext/couchbase/core/impl/dns_srv_tracker.cxx +45 -18
  76. data/ext/couchbase/core/impl/error.cxx +22 -2
  77. data/ext/couchbase/core/impl/internal_analytics_stream_result.hxx +111 -0
  78. data/ext/couchbase/core/impl/internal_query_stream_result.hxx +110 -0
  79. data/ext/couchbase/core/impl/invoke_with_node_id.hxx +15 -7
  80. data/ext/couchbase/core/impl/key_value_error_category.cxx +6 -0
  81. data/ext/couchbase/core/impl/lookup_in_replica.cxx +10 -10
  82. data/ext/couchbase/core/impl/lookup_in_replica.hxx +4 -4
  83. data/ext/couchbase/core/impl/node_id.cxx +49 -13
  84. data/ext/couchbase/core/impl/observability_recorder.cxx +12 -2
  85. data/ext/couchbase/core/impl/observe_poll.cxx +63 -23
  86. data/ext/couchbase/core/impl/public_analytics_stream_result.cxx +372 -0
  87. data/ext/couchbase/core/impl/public_bucket.cxx +48 -2
  88. data/ext/couchbase/core/impl/public_cluster.cxx +229 -42
  89. data/ext/couchbase/core/impl/public_query_stream_result.cxx +380 -0
  90. data/ext/couchbase/core/impl/public_transaction_get_multi_replicas_from_preferred_server_group_result.cxx +42 -0
  91. data/ext/couchbase/core/impl/public_transaction_get_multi_result.cxx +42 -0
  92. data/ext/couchbase/core/impl/query.cxx +76 -7
  93. data/ext/couchbase/core/impl/query.hxx +36 -0
  94. data/ext/couchbase/core/impl/query_index_manager.cxx +54 -1
  95. data/ext/couchbase/core/impl/replica_utils.cxx +101 -0
  96. data/ext/couchbase/core/impl/replica_utils.hxx +64 -0
  97. data/ext/couchbase/core/impl/resolve_node_id.hxx +125 -0
  98. data/ext/couchbase/core/impl/scope.cxx +70 -0
  99. data/ext/couchbase/core/impl/search.cxx +31 -1
  100. data/ext/couchbase/core/impl/transactions.cxx +130 -0
  101. data/ext/couchbase/core/impl/wait_until_ready.cxx +439 -0
  102. data/ext/couchbase/core/impl/wait_until_ready.hxx +110 -0
  103. data/ext/couchbase/core/impl/with_bucket_config_or_timeout.hxx +180 -0
  104. data/ext/couchbase/core/impl/with_cancellation.hxx +11 -3
  105. data/ext/couchbase/core/io/configuration_belongs_to_session.hxx +1 -2
  106. data/ext/couchbase/core/io/dns_client.cxx +122 -45
  107. data/ext/couchbase/core/io/dns_codec.hxx +21 -21
  108. data/ext/couchbase/core/io/dns_config.cxx +21 -6
  109. data/ext/couchbase/core/io/http_command.hxx +149 -121
  110. data/ext/couchbase/core/io/http_error.hxx +107 -0
  111. data/ext/couchbase/core/io/http_parser.cxx +4 -0
  112. data/ext/couchbase/core/io/http_session.cxx +606 -154
  113. data/ext/couchbase/core/io/http_session.hxx +147 -30
  114. data/ext/couchbase/core/io/http_session_manager.hxx +329 -382
  115. data/ext/couchbase/core/io/http_streaming_parser.cxx +4 -0
  116. data/ext/couchbase/core/io/http_streaming_response.cxx +328 -43
  117. data/ext/couchbase/core/io/http_streaming_response.hxx +37 -3
  118. data/ext/couchbase/core/io/mcbp_buffer_pool.hxx +122 -0
  119. data/ext/couchbase/core/io/mcbp_command.hxx +150 -51
  120. data/ext/couchbase/core/io/mcbp_command_id.hxx +45 -0
  121. data/ext/couchbase/core/io/mcbp_message.cxx +9 -1
  122. data/ext/couchbase/core/io/mcbp_message.hxx +19 -0
  123. data/ext/couchbase/core/io/mcbp_output_queue.hxx +150 -0
  124. data/ext/couchbase/core/io/mcbp_parser.cxx +24 -7
  125. data/ext/couchbase/core/io/mcbp_session.cxx +309 -301
  126. data/ext/couchbase/core/io/mcbp_session.hxx +27 -18
  127. data/ext/couchbase/core/io/opaque_ring_table.hxx +145 -0
  128. data/ext/couchbase/core/io/retry_orchestrator.hxx +6 -5
  129. data/ext/couchbase/core/io/stream_deadline.hxx +50 -0
  130. data/ext/couchbase/core/io/streams.cxx +151 -21
  131. data/ext/couchbase/core/io/streams.hxx +48 -1
  132. data/ext/couchbase/core/logger/logger.cxx +36 -0
  133. data/ext/couchbase/core/logger/logger.hxx +46 -6
  134. data/ext/couchbase/core/logger/redaction.hxx +503 -0
  135. data/ext/couchbase/core/management/eventing_status.hxx +10 -0
  136. data/ext/couchbase/core/management/eventing_status_json.hxx +4 -0
  137. data/ext/couchbase/core/mcbp/big_endian.cxx +1 -1
  138. data/ext/couchbase/core/mcbp/codec.cxx +27 -18
  139. data/ext/couchbase/core/mcbp/operation_queue.cxx +2 -2
  140. data/ext/couchbase/core/mcbp/packet.hxx +2 -2
  141. data/ext/couchbase/core/mcbp/queue_request.cxx +23 -6
  142. data/ext/couchbase/core/mcbp/queue_request.hxx +21 -0
  143. data/ext/couchbase/core/meta/features.hxx +13 -0
  144. data/ext/couchbase/core/meta/version.cxx +6 -3
  145. data/ext/couchbase/core/metrics/logging_meter.cxx +5 -10
  146. data/ext/couchbase/core/metrics/meter_wrapper.cxx +63 -33
  147. data/ext/couchbase/core/metrics/meter_wrapper.hxx +55 -3
  148. data/ext/couchbase/core/operations/analytics_response_parsing.cxx +177 -0
  149. data/ext/couchbase/core/operations/analytics_response_parsing.hxx +55 -0
  150. data/ext/couchbase/core/operations/document_analytics.cxx +48 -130
  151. data/ext/couchbase/core/operations/document_analytics.hxx +14 -2
  152. data/ext/couchbase/core/operations/document_get_all_replicas.hxx +15 -7
  153. data/ext/couchbase/core/operations/document_get_any_replica.hxx +19 -8
  154. data/ext/couchbase/core/operations/document_get_projected.cxx +1 -1
  155. data/ext/couchbase/core/{impl/get_replica.cxx → operations/document_get_replica.cxx} +21 -3
  156. data/ext/couchbase/core/{impl/get_replica.hxx → operations/document_get_replica.hxx} +31 -4
  157. data/ext/couchbase/core/operations/document_lookup_in.cxx +10 -10
  158. data/ext/couchbase/core/operations/document_lookup_in_all_replicas.hxx +228 -198
  159. data/ext/couchbase/core/operations/document_lookup_in_any_replica.hxx +215 -217
  160. data/ext/couchbase/core/operations/document_query.cxx +108 -221
  161. data/ext/couchbase/core/operations/document_query.hxx +18 -4
  162. data/ext/couchbase/core/operations/document_search.cxx +52 -8
  163. data/ext/couchbase/core/operations/document_search.hxx +3 -0
  164. data/ext/couchbase/core/operations/document_view.cxx +3 -3
  165. data/ext/couchbase/core/operations/management/analytics_dataset_create.cxx +15 -8
  166. data/ext/couchbase/core/operations/management/analytics_dataset_create.hxx +4 -0
  167. data/ext/couchbase/core/operations/management/analytics_dataset_drop.cxx +11 -6
  168. data/ext/couchbase/core/operations/management/analytics_dataset_get_all.cxx +3 -2
  169. data/ext/couchbase/core/operations/management/analytics_dataverse_create.cxx +10 -5
  170. data/ext/couchbase/core/operations/management/analytics_dataverse_drop.cxx +10 -5
  171. data/ext/couchbase/core/operations/management/analytics_get_pending_mutations.cxx +2 -1
  172. data/ext/couchbase/core/operations/management/analytics_index_create.cxx +33 -8
  173. data/ext/couchbase/core/operations/management/analytics_index_drop.cxx +12 -7
  174. data/ext/couchbase/core/operations/management/analytics_index_get_all.cxx +3 -2
  175. data/ext/couchbase/core/operations/management/analytics_link_connect.cxx +11 -6
  176. data/ext/couchbase/core/operations/management/analytics_link_create.cxx +3 -3
  177. data/ext/couchbase/core/operations/management/analytics_link_disconnect.cxx +10 -4
  178. data/ext/couchbase/core/operations/management/analytics_link_drop.cxx +6 -4
  179. data/ext/couchbase/core/operations/management/analytics_link_get_all.cxx +4 -3
  180. data/ext/couchbase/core/operations/management/analytics_link_replace.cxx +3 -3
  181. data/ext/couchbase/core/operations/management/analytics_link_utils.hxx +1 -1
  182. data/ext/couchbase/core/operations/management/change_password.cxx +2 -0
  183. data/ext/couchbase/core/operations/management/collection_drop.cxx +5 -1
  184. data/ext/couchbase/core/operations/management/error_utils.cxx +59 -5
  185. data/ext/couchbase/core/operations/management/error_utils.hxx +29 -1
  186. data/ext/couchbase/core/operations/management/eventing_deploy_function.cxx +9 -3
  187. data/ext/couchbase/core/operations/management/eventing_drop_function.cxx +8 -3
  188. data/ext/couchbase/core/operations/management/eventing_get_all_functions.cxx +4 -2
  189. data/ext/couchbase/core/operations/management/eventing_get_function.cxx +5 -3
  190. data/ext/couchbase/core/operations/management/eventing_get_status.cxx +4 -2
  191. data/ext/couchbase/core/operations/management/eventing_pause_function.cxx +9 -3
  192. data/ext/couchbase/core/operations/management/eventing_resume_function.cxx +9 -3
  193. data/ext/couchbase/core/operations/management/eventing_undeploy_function.cxx +9 -3
  194. data/ext/couchbase/core/operations/management/eventing_upsert_function.cxx +9 -3
  195. data/ext/couchbase/core/operations/management/group_drop.cxx +3 -1
  196. data/ext/couchbase/core/operations/management/group_get.cxx +3 -1
  197. data/ext/couchbase/core/operations/management/group_upsert.cxx +11 -8
  198. data/ext/couchbase/core/operations/management/query_index_build.cxx +5 -2
  199. data/ext/couchbase/core/operations/management/query_index_create.cxx +9 -3
  200. data/ext/couchbase/core/operations/management/query_index_drop.cxx +11 -4
  201. data/ext/couchbase/core/operations/management/query_index_get_all.cxx +1 -1
  202. data/ext/couchbase/core/operations/management/query_index_get_all_deferred.cxx +1 -1
  203. data/ext/couchbase/core/operations/management/scope_drop.cxx +5 -1
  204. data/ext/couchbase/core/operations/management/scope_get_all.cxx +6 -1
  205. data/ext/couchbase/core/operations/management/search_get_stats.cxx +10 -0
  206. data/ext/couchbase/core/operations/management/search_index_analyze_document.cxx +3 -2
  207. data/ext/couchbase/core/operations/management/search_index_control_ingest.cxx +4 -3
  208. data/ext/couchbase/core/operations/management/search_index_control_plan_freeze.cxx +4 -3
  209. data/ext/couchbase/core/operations/management/search_index_control_query.cxx +4 -3
  210. data/ext/couchbase/core/operations/management/search_index_drop.cxx +2 -2
  211. data/ext/couchbase/core/operations/management/search_index_get.cxx +2 -2
  212. data/ext/couchbase/core/operations/management/search_index_get_documents_count.cxx +3 -2
  213. data/ext/couchbase/core/operations/management/search_index_get_stats.cxx +3 -1
  214. data/ext/couchbase/core/operations/management/search_index_upsert.cxx +2 -2
  215. data/ext/couchbase/core/operations/management/user_drop.cxx +3 -1
  216. data/ext/couchbase/core/operations/management/user_get.cxx +3 -1
  217. data/ext/couchbase/core/operations/management/user_upsert.cxx +12 -9
  218. data/ext/couchbase/core/operations/management/view_index_drop.cxx +1 -1
  219. data/ext/couchbase/core/operations/management/view_index_get.cxx +1 -1
  220. data/ext/couchbase/core/operations/management/view_index_upsert.cxx +1 -1
  221. data/ext/couchbase/core/operations/operation_traits.hxx +18 -0
  222. data/ext/couchbase/core/operations/query_response_parsing.cxx +211 -0
  223. data/ext/couchbase/core/operations/query_response_parsing.hxx +60 -0
  224. data/ext/couchbase/core/operations_fwd.hxx +3 -3
  225. data/ext/couchbase/core/origin.cxx +54 -26
  226. data/ext/couchbase/core/origin.hxx +12 -0
  227. data/ext/couchbase/core/orphan_reporter.cxx +2 -1
  228. data/ext/couchbase/core/platform/random.cc +7 -7
  229. data/ext/couchbase/core/protocol/client_request.cxx +2 -2
  230. data/ext/couchbase/core/protocol/client_request.hxx +38 -21
  231. data/ext/couchbase/core/protocol/client_response.cxx +11 -3
  232. data/ext/couchbase/core/protocol/client_response.hxx +27 -6
  233. data/ext/couchbase/core/protocol/cmd_append.cxx +2 -2
  234. data/ext/couchbase/core/protocol/cmd_cluster_map_change_notification.cxx +2 -2
  235. data/ext/couchbase/core/protocol/cmd_decrement.cxx +6 -6
  236. data/ext/couchbase/core/protocol/cmd_get.cxx +1 -1
  237. data/ext/couchbase/core/protocol/cmd_get_and_lock.cxx +2 -2
  238. data/ext/couchbase/core/protocol/cmd_get_and_touch.cxx +2 -2
  239. data/ext/couchbase/core/protocol/cmd_get_cluster_config.cxx +6 -4
  240. data/ext/couchbase/core/protocol/cmd_get_collection_id.cxx +2 -2
  241. data/ext/couchbase/core/protocol/cmd_get_error_map.cxx +1 -1
  242. data/ext/couchbase/core/protocol/cmd_get_meta.cxx +4 -4
  243. data/ext/couchbase/core/protocol/cmd_get_replica.cxx +1 -1
  244. data/ext/couchbase/core/protocol/cmd_hello.cxx +1 -1
  245. data/ext/couchbase/core/protocol/cmd_increment.cxx +6 -6
  246. data/ext/couchbase/core/protocol/cmd_insert.cxx +4 -4
  247. data/ext/couchbase/core/protocol/cmd_lookup_in.cxx +4 -3
  248. data/ext/couchbase/core/protocol/cmd_lookup_in_replica.cxx +4 -3
  249. data/ext/couchbase/core/protocol/cmd_mutate_in.cxx +10 -9
  250. data/ext/couchbase/core/protocol/cmd_mutate_in.hxx +10 -10
  251. data/ext/couchbase/core/protocol/cmd_observe_seqno.cxx +7 -7
  252. data/ext/couchbase/core/protocol/cmd_prepend.cxx +2 -2
  253. data/ext/couchbase/core/protocol/cmd_remove.cxx +2 -2
  254. data/ext/couchbase/core/protocol/cmd_replace.cxx +4 -4
  255. data/ext/couchbase/core/protocol/cmd_touch.cxx +1 -1
  256. data/ext/couchbase/core/protocol/cmd_upsert.cxx +4 -4
  257. data/ext/couchbase/core/protocol/datatype.hxx +118 -1
  258. data/ext/couchbase/core/protocol/frame_info_utils.cxx +1 -1
  259. data/ext/couchbase/core/protocol/magic.hxx +4 -0
  260. data/ext/couchbase/core/protocol/magic_fmt.hxx +3 -0
  261. data/ext/couchbase/core/protocol/server_request.hxx +3 -1
  262. data/ext/couchbase/core/protocol/status.cxx +1 -1
  263. data/ext/couchbase/core/protostellar/analytics_converter.hxx +171 -0
  264. data/ext/couchbase/core/protostellar/bucket_admin_converter.hxx +301 -0
  265. data/ext/couchbase/core/protostellar/collection_admin_converter.hxx +92 -0
  266. data/ext/couchbase/core/protostellar/component.cxx +2445 -0
  267. data/ext/couchbase/core/protostellar/component.hxx +391 -0
  268. data/ext/couchbase/core/{columnar/bootstrap_notification_subscriber.hxx → protostellar/compression_settings.hxx} +11 -10
  269. data/ext/couchbase/core/protostellar/credentials.cxx +233 -0
  270. data/ext/couchbase/core/protostellar/credentials.hxx +88 -0
  271. data/ext/couchbase/core/protostellar/dispatcher.cxx +57 -0
  272. data/ext/couchbase/core/protostellar/dispatcher.hxx +482 -0
  273. data/ext/couchbase/core/protostellar/error_utils.cxx +293 -0
  274. data/ext/couchbase/core/protostellar/error_utils.hxx +97 -0
  275. data/ext/couchbase/core/protostellar/json_payload.hxx +49 -0
  276. data/ext/couchbase/core/protostellar/kv_converter.cxx +70 -0
  277. data/ext/couchbase/core/protostellar/kv_converter.hxx +600 -0
  278. data/ext/couchbase/core/protostellar/query_converter.hxx +265 -0
  279. data/ext/couchbase/core/protostellar/query_index_admin_converter.hxx +291 -0
  280. data/ext/couchbase/core/protostellar/query_proto.hxx +73 -0
  281. data/ext/couchbase/core/protostellar/search_converter.hxx +244 -0
  282. data/ext/couchbase/core/protostellar/search_index_admin_converter.hxx +156 -0
  283. data/ext/couchbase/core/protostellar/view_converter.hxx +158 -0
  284. data/ext/couchbase/core/query_stream.cxx +447 -0
  285. data/ext/couchbase/core/query_stream.hxx +141 -0
  286. data/ext/couchbase/core/query_stream_component.cxx +243 -0
  287. data/ext/couchbase/core/query_stream_component.hxx +68 -0
  288. data/ext/couchbase/core/range_scan_load_balancer.cxx +15 -8
  289. data/ext/couchbase/core/range_scan_orchestrator.cxx +15 -3
  290. data/ext/couchbase/core/response_handler.hxx +41 -4
  291. data/ext/couchbase/core/row_streamer.cxx +332 -46
  292. data/ext/couchbase/core/row_streamer.hxx +31 -1
  293. data/ext/couchbase/core/row_streamer_options.hxx +55 -0
  294. data/ext/couchbase/core/sasl/client.h +3 -0
  295. data/ext/couchbase/core/search_scoring.hxx +66 -0
  296. data/ext/couchbase/core/stream_error_details.hxx +69 -0
  297. data/ext/couchbase/core/timeout_defaults.hxx +0 -1
  298. data/ext/couchbase/core/topology/capabilities.hxx +6 -0
  299. data/ext/couchbase/core/topology/capabilities_fmt.hxx +3 -0
  300. data/ext/couchbase/core/topology/configuration.cxx +21 -6
  301. data/ext/couchbase/core/topology/configuration.hxx +29 -8
  302. data/ext/couchbase/core/topology/configuration_json.hxx +3 -0
  303. data/ext/couchbase/core/topology/error_map_json.hxx +3 -1
  304. data/ext/couchbase/core/tracing/threshold_logging_tracer.cxx +70 -4
  305. data/ext/couchbase/core/tracing/threshold_logging_tracer.hxx +10 -0
  306. data/ext/couchbase/core/transactions/active_transaction_record.cxx +0 -34
  307. data/ext/couchbase/core/transactions/attempt_context_impl.cxx +108 -63
  308. data/ext/couchbase/core/transactions/attempt_context_impl.hxx +19 -2
  309. data/ext/couchbase/core/transactions/error_list.hxx +2 -2
  310. data/ext/couchbase/core/transactions/get_multi_fetch.hxx +160 -0
  311. data/ext/couchbase/core/transactions/get_multi_orchestrator.cxx +326 -125
  312. data/ext/couchbase/core/transactions/get_multi_transaction_id.hxx +62 -0
  313. data/ext/couchbase/core/transactions/internal/atr_entry.hxx +22 -2
  314. data/ext/couchbase/core/transactions/internal/transaction_context.hxx +2 -2
  315. data/ext/couchbase/core/transactions/internal/transactions_cleanup.hxx +23 -1
  316. data/ext/couchbase/core/transactions/internal/utils.hxx +50 -14
  317. data/ext/couchbase/core/transactions/staged_mutation.cxx +23 -18
  318. data/ext/couchbase/core/transactions/staged_mutation.hxx +15 -4
  319. data/ext/couchbase/core/transactions/transaction_context.cxx +55 -40
  320. data/ext/couchbase/core/transactions/transaction_get_result.hxx +16 -0
  321. data/ext/couchbase/core/transactions/transactions.cxx +3 -55
  322. data/ext/couchbase/core/transactions/transactions_cleanup.cxx +165 -72
  323. data/ext/couchbase/core/transactions/transactions_config.cxx +0 -11
  324. data/ext/couchbase/core/transactions/utils.cxx +10 -0
  325. data/ext/couchbase/core/transactions/waitable_op_list.hxx +2 -2
  326. data/ext/couchbase/core/transactions.hxx +9 -9
  327. data/ext/couchbase/core/utils/byteswap.hxx +166 -9
  328. data/ext/couchbase/core/utils/connection_string.cxx +50 -85
  329. data/ext/couchbase/core/utils/connection_string.hxx +15 -0
  330. data/ext/couchbase/core/{columnar/backoff_calculator.hxx → utils/deadline.hxx} +13 -13
  331. data/ext/couchbase/core/utils/duration_parser.cxx +1 -1
  332. data/ext/couchbase/core/utils/json_streaming_lexer.cxx +48 -5
  333. data/ext/couchbase/core/utils/json_streaming_lexer.hxx +4 -1
  334. data/ext/couchbase/core/utils/movable_function.hxx +301 -52
  335. data/ext/couchbase/core/utils/name_codec.hxx +154 -11
  336. data/ext/couchbase/core/{columnar/retry_info.hxx → utils/process_id.hxx} +18 -13
  337. data/ext/couchbase/core/utils/url_codec.cxx +12 -51
  338. data/ext/couchbase/core/websocket_codec.cxx +3 -29
  339. data/ext/couchbase/couchbase/analytics_options.hxx +21 -10
  340. data/ext/couchbase/couchbase/analytics_row.hxx +105 -0
  341. data/ext/couchbase/couchbase/analytics_stream_result.hxx +266 -0
  342. data/ext/couchbase/couchbase/boolean_query.hxx +3 -3
  343. data/ext/couchbase/couchbase/bucket.hxx +57 -0
  344. data/ext/couchbase/couchbase/cluster.hxx +183 -5
  345. data/ext/couchbase/{core/columnar/security_options.hxx → couchbase/cluster_state.hxx} +18 -14
  346. data/ext/couchbase/couchbase/codec/lenient_json_transcoder.hxx +69 -0
  347. data/ext/couchbase/couchbase/collection.hxx +234 -14
  348. data/ext/couchbase/couchbase/common_durability_options.hxx +18 -3
  349. data/ext/couchbase/couchbase/conjunction_query.hxx +1 -1
  350. data/ext/couchbase/couchbase/create_dataset_analytics_options.hxx +6 -1
  351. data/ext/couchbase/couchbase/date_range_query.hxx +2 -2
  352. data/ext/couchbase/couchbase/decrement_options.hxx +1 -1
  353. data/ext/couchbase/couchbase/disjunction_query.hxx +1 -1
  354. data/ext/couchbase/couchbase/error.hxx +32 -0
  355. data/ext/couchbase/couchbase/error_codes.hxx +32 -0
  356. data/ext/couchbase/couchbase/geo_bounding_box_query.hxx +1 -1
  357. data/ext/couchbase/couchbase/geo_distance_query.hxx +1 -1
  358. data/ext/couchbase/couchbase/geo_polygon_query.hxx +1 -1
  359. data/ext/couchbase/couchbase/get_replica_options.hxx +68 -0
  360. data/ext/couchbase/couchbase/get_replica_result.hxx +5 -3
  361. data/ext/couchbase/couchbase/get_replica_strategy.hxx +161 -0
  362. data/ext/couchbase/couchbase/get_result.hxx +1 -0
  363. data/ext/couchbase/couchbase/increment_options.hxx +1 -1
  364. data/ext/couchbase/couchbase/insert_options.hxx +1 -1
  365. data/ext/couchbase/couchbase/match_phrase_query.hxx +1 -1
  366. data/ext/couchbase/couchbase/match_query.hxx +1 -1
  367. data/ext/couchbase/couchbase/mutate_in_options.hxx +3 -3
  368. data/ext/couchbase/couchbase/network_options.hxx +1 -1
  369. data/ext/couchbase/couchbase/node_id.hxx +42 -14
  370. data/ext/couchbase/couchbase/node_id_for_options.hxx +7 -1
  371. data/ext/couchbase/couchbase/node_ids_options.hxx +8 -2
  372. data/ext/couchbase/couchbase/numeric_range_query.hxx +1 -1
  373. data/ext/couchbase/couchbase/phrase_query.hxx +1 -1
  374. data/ext/couchbase/couchbase/prefix_query.hxx +1 -1
  375. data/ext/couchbase/couchbase/query_options.hxx +23 -12
  376. data/ext/couchbase/couchbase/query_row.hxx +111 -0
  377. data/ext/couchbase/couchbase/query_stream_result.hxx +302 -0
  378. data/ext/couchbase/couchbase/query_string_query.hxx +3 -3
  379. data/ext/couchbase/couchbase/regexp_query.hxx +1 -1
  380. data/ext/couchbase/couchbase/replace_options.hxx +3 -3
  381. data/ext/couchbase/couchbase/result.hxx +14 -3
  382. data/ext/couchbase/couchbase/scan_result_item.hxx +1 -0
  383. data/ext/couchbase/couchbase/scope.hxx +85 -2
  384. data/ext/couchbase/couchbase/search_options.hxx +58 -8
  385. data/ext/couchbase/couchbase/search_scoring.hxx +94 -0
  386. data/ext/couchbase/couchbase/search_scoring_none.hxx +51 -0
  387. data/ext/couchbase/couchbase/search_scoring_reciprocal_rank_fusion.hxx +88 -0
  388. data/ext/couchbase/couchbase/search_scoring_relative_score_fusion.hxx +70 -0
  389. data/ext/couchbase/couchbase/term_range_query.hxx +1 -1
  390. data/ext/couchbase/couchbase/tracing/request_span.hxx +46 -0
  391. data/ext/couchbase/couchbase/transactions/transaction_get_multi_replicas_from_preferred_server_group_result.hxx +23 -21
  392. data/ext/couchbase/couchbase/transactions/transaction_get_multi_result.hxx +24 -19
  393. data/ext/couchbase/couchbase/transactions/transaction_get_result.hxx +17 -3
  394. data/ext/couchbase/couchbase/transactions/transactions_config.hxx +4 -2
  395. data/ext/couchbase/couchbase/transactions.hxx +27 -18
  396. data/ext/couchbase/couchbase/upsert_options.hxx +3 -3
  397. data/ext/couchbase/couchbase/vector_query.hxx +1 -1
  398. data/ext/couchbase/couchbase/wait_until_ready_options.hxx +111 -0
  399. data/ext/couchbase/couchbase/wildcard_query.hxx +1 -1
  400. data/ext/extconf.rb +15 -10
  401. data/ext/rcb_analytics.cxx +82 -102
  402. data/ext/rcb_backend.cxx +42 -36
  403. data/ext/rcb_backend.hxx +2 -0
  404. data/ext/rcb_buckets.cxx +47 -59
  405. data/ext/rcb_collections.cxx +42 -52
  406. data/ext/rcb_crud.cxx +345 -224
  407. data/ext/rcb_diagnostics.cxx +117 -27
  408. data/ext/rcb_exceptions.cxx +152 -99
  409. data/ext/rcb_exceptions.hxx +25 -0
  410. data/ext/rcb_extras.cxx +18 -19
  411. data/ext/rcb_hdr_histogram.cxx +19 -4
  412. data/ext/rcb_logger.cxx +202 -27
  413. data/ext/rcb_logger.hxx +12 -0
  414. data/ext/rcb_multi.cxx +40 -40
  415. data/ext/rcb_observability.cxx +7 -5
  416. data/ext/rcb_query.cxx +99 -142
  417. data/ext/rcb_range_scan.cxx +41 -35
  418. data/ext/rcb_search.cxx +98 -99
  419. data/ext/rcb_users.cxx +36 -56
  420. data/ext/rcb_utils.cxx +100 -37
  421. data/ext/rcb_utils.hxx +287 -33
  422. data/ext/rcb_version.cxx +1 -1
  423. data/ext/rcb_views.cxx +55 -51
  424. data/lib/active_support/cache/couchbase_store.rb +77 -12
  425. data/lib/couchbase/bucket.rb +20 -0
  426. data/lib/couchbase/cluster.rb +17 -0
  427. data/lib/couchbase/collection.rb +36 -1
  428. data/lib/couchbase/errors.rb +18 -0
  429. data/lib/couchbase/fork_hooks.rb +16 -7
  430. data/lib/couchbase/get_replica_strategy.rb +89 -0
  431. data/lib/couchbase/logger.rb +1 -1
  432. data/lib/couchbase/management/analytics_index_manager.rb +15 -15
  433. data/lib/couchbase/management/bucket_manager.rb +6 -6
  434. data/lib/couchbase/management/collection_manager.rb +6 -6
  435. data/lib/couchbase/management/query_index_manager.rb +7 -7
  436. data/lib/couchbase/management/search_index_manager.rb +13 -13
  437. data/lib/couchbase/management/user_manager.rb +10 -10
  438. data/lib/couchbase/management/view_index_manager.rb +5 -5
  439. data/lib/couchbase/options.rb +174 -42
  440. data/lib/couchbase/protostellar/bucket.rb +4 -0
  441. data/lib/couchbase/protostellar/cluster.rb +4 -0
  442. data/lib/couchbase/protostellar/collection.rb +4 -0
  443. data/lib/couchbase/protostellar/error_handling.rb +2 -1
  444. data/lib/couchbase/protostellar/request.rb +1 -0
  445. data/lib/couchbase/protostellar/request_generator/kv.rb +16 -2
  446. data/lib/couchbase/protostellar/request_generator/search.rb +17 -1
  447. data/lib/couchbase/protostellar/retry/orchestrator.rb +3 -2
  448. data/lib/couchbase/protostellar/retry/strategies/fail_fast.rb +33 -0
  449. data/lib/couchbase/protostellar/retry/strategies.rb +1 -0
  450. data/lib/couchbase/search_options.rb +95 -6
  451. data/lib/couchbase/version.rb +1 -1
  452. metadata +91 -33
  453. data/ext/0001-fix-build-for-mingw-w64-ucrt-x86_64-toolchain.patch +0 -40
  454. data/ext/couchbase/core/columnar/agent.hxx +0 -71
  455. data/ext/couchbase/core/columnar/agent_config.hxx +0 -59
  456. data/ext/couchbase/core/columnar/background_bootstrap_listener.hxx +0 -42
  457. data/ext/couchbase/core/columnar/backoff_calculator.cxx +0 -62
  458. data/ext/couchbase/core/columnar/columnar_agent.cxx +0 -147
  459. data/ext/couchbase/core/columnar/columnar_agent_config.cxx +0 -48
  460. data/ext/couchbase/core/columnar/columnar_error.cxx +0 -51
  461. data/ext/couchbase/core/columnar/database_management_options.hxx +0 -56
  462. data/ext/couchbase/core/columnar/error.hxx +0 -51
  463. data/ext/couchbase/core/columnar/error_codes.cxx +0 -107
  464. data/ext/couchbase/core/columnar/error_codes.hxx +0 -75
  465. data/ext/couchbase/core/columnar/management_component.cxx +0 -300
  466. data/ext/couchbase/core/columnar/management_component.hxx +0 -56
  467. data/ext/couchbase/core/columnar/query_component.cxx +0 -523
  468. data/ext/couchbase/core/columnar/query_component.hxx +0 -57
  469. data/ext/couchbase/core/columnar/query_options.hxx +0 -59
  470. data/ext/couchbase/core/columnar/query_result.cxx +0 -130
  471. data/ext/couchbase/core/columnar/query_result.hxx +0 -78
  472. data/ext/couchbase/core/io/config_tracker.cxx +0 -687
  473. data/ext/couchbase/core/io/config_tracker.hxx +0 -123
@@ -4,6 +4,80 @@ include(CMakePackageConfigHelpers)
4
4
  install(DIRECTORY ${PROJECT_SOURCE_DIR}/couchbase DESTINATION ${CMAKE_INSTALL_INCLUDEDIR})
5
5
  install(FILES LICENSE.txt DESTINATION ${CMAKE_INSTALL_DOCDIR})
6
6
 
7
+
8
+ # Notices for everything compiled into the binaries.
9
+ #
10
+ # Vendoring moved these dependencies from distribution packages -- each of which carried its own
11
+ # licence -- into our own artefacts, so the obligation to ship their terms moved with them. Apache
12
+ # 2.0 requires the NOTICE file to travel with any distribution of the work (gRPC, Protobuf, Abseil),
13
+ # and the BSD/MIT projects require their copyright notice to be reproduced (BoringSSL, re2, c-ares,
14
+ # zlib, curl, utf8_range).
15
+ #
16
+ # Installed only when the dependency was actually built from source: a build that links the
17
+ # platform's gRPC ships none of its code and owes nothing.
18
+ function(couchbase_install_third_party_licence name)
19
+ set(_found FALSE)
20
+ foreach(candidate IN LISTS ARGN)
21
+ if(candidate AND EXISTS "${candidate}")
22
+ install(FILES "${candidate}" DESTINATION "${CMAKE_INSTALL_DOCDIR}/third_party/${name}")
23
+ set(_found TRUE)
24
+ endif()
25
+ endforeach()
26
+ # Said out loud, because a licence that quietly fails to install looks exactly like one that was
27
+ # never required. cli11 went missing this way: it is added from tools/CMakeLists.txt, so its
28
+ # source directory is a child-scope variable and is simply empty here.
29
+ if(NOT _found)
30
+ message(WARNING "No licence file found for vendored component '${name}'; it will not ship with "
31
+ "the packages even though its code may be compiled in. Checked: ${ARGN}")
32
+ endif()
33
+ endfunction()
34
+
35
+ if(boringssl_SOURCE_DIR)
36
+ couchbase_install_third_party_licence(boringssl "${boringssl_SOURCE_DIR}/LICENSE")
37
+ endif()
38
+ if(curl_SOURCE_DIR)
39
+ couchbase_install_third_party_licence(curl "${curl_SOURCE_DIR}/COPYING")
40
+ endif()
41
+ if(opentelemetry_SOURCE_DIR)
42
+ # Statically linked into cbc and fit_performer through the OTLP exporters; the library itself uses
43
+ # only the header-only API, which is equally contained.
44
+ couchbase_install_third_party_licence(opentelemetry-cpp "${opentelemetry_SOURCE_DIR}/LICENSE")
45
+ endif()
46
+ if(grpc_SOURCE_DIR)
47
+ couchbase_install_third_party_licence(grpc "${grpc_SOURCE_DIR}/LICENSE" "${grpc_SOURCE_DIR}/NOTICE.txt")
48
+ # Fetched as submodules of gRPC and compiled into the same binaries, so their notices ship too.
49
+ couchbase_install_third_party_licence(abseil-cpp "${grpc_SOURCE_DIR}/third_party/abseil-cpp/LICENSE")
50
+ couchbase_install_third_party_licence(protobuf "${grpc_SOURCE_DIR}/third_party/protobuf/LICENSE")
51
+ couchbase_install_third_party_licence(re2 "${grpc_SOURCE_DIR}/third_party/re2/LICENSE")
52
+ couchbase_install_third_party_licence(c-ares "${grpc_SOURCE_DIR}/third_party/cares/cares/LICENSE.md")
53
+ couchbase_install_third_party_licence(zlib "${grpc_SOURCE_DIR}/third_party/zlib/LICENSE")
54
+ couchbase_install_third_party_licence(utf8_range
55
+ "${grpc_SOURCE_DIR}/third_party/protobuf/third_party/utf8_range/LICENSE")
56
+ endif()
57
+ if(api_common_protos_SOURCE_DIR)
58
+ couchbase_install_third_party_licence(api-common-protos "${api_common_protos_SOURCE_DIR}/LICENSE")
59
+ endif()
60
+
61
+ # The SDK's own bundled dependencies. These are compiled into the client library in every
62
+ # configuration, and since the tools packages stopped depending on the library package they are
63
+ # carried inside cbc and fit_performer as well, so the same obligation applies to those packages.
64
+ couchbase_install_third_party_licence(spdlog "${spdlog_SOURCE_DIR}/LICENSE")
65
+ couchbase_install_third_party_licence(fmt "${fmt_SOURCE_DIR}/LICENSE.txt"
66
+ "${spdlog_SOURCE_DIR}/include/spdlog/fmt/bundled/fmt.license.rst")
67
+ couchbase_install_third_party_licence(hdr_histogram "${hdr_histogram_SOURCE_DIR}/COPYING.txt")
68
+ couchbase_install_third_party_licence(snappy "${snappy_SOURCE_DIR}/COPYING")
69
+ couchbase_install_third_party_licence(llhttp "${llhttp_SOURCE_DIR}/LICENSE-MIT")
70
+ couchbase_install_third_party_licence(json "${json_SOURCE_DIR}/LICENSE")
71
+ couchbase_install_third_party_licence(gsl "${gsl_SOURCE_DIR}/LICENSE")
72
+ # Only fetched when the tools are built, and only cbc contains it.
73
+ if(COUCHBASE_CXX_CLIENT_BUILD_TOOLS)
74
+ couchbase_install_third_party_licence(cli11 "${cli11_SOURCE_DIR}/LICENSE")
75
+ endif()
76
+ couchbase_install_third_party_licence(asio "${asio_SOURCE_DIR}/asio/LICENSE_1_0.txt")
77
+ # Checked into this repository rather than fetched, so their paths are fixed.
78
+ couchbase_install_third_party_licence(expected "${PROJECT_SOURCE_DIR}/third_party/expected/COPYING")
79
+ couchbase_install_third_party_licence(jsonsl "${PROJECT_SOURCE_DIR}/third_party/jsonsl/LICENSE")
80
+
7
81
  set(COUCHBASE_CXX_CLIENT_PKGCONFIG_VERSION
8
82
  "${COUCHBASE_CXX_CLIENT_SEMVER}"
9
83
  CACHE STRING "The version to use in couchbase_cxx_client.pc")
@@ -17,11 +91,213 @@ install(FILES ${PROJECT_BINARY_DIR}/couchbase_cxx_client-version.cmake
17
91
 
18
92
  if(COUCHBASE_CXX_CLIENT_BUILD_TOOLS)
19
93
  install(TARGETS cbc RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR})
94
+ # fit_performer is packaged separately (couchbase-cxx-client-fit-performer) so nothing
95
+ # depends on it automatically; it is built against the shared SDK for integration testing.
96
+ if(TARGET fit_performer)
97
+ install(TARGETS fit_performer RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR})
98
+ endif()
20
99
  endif()
21
100
 
22
101
  if(COUCHBASE_CXX_CLIENT_BUILD_STATIC)
23
102
  get_target_property(couchbase_cxx_client_static_IMPORTED_LOCATION couchbase_cxx_client_static IMPORTED_LOCATION)
24
103
 
104
+ # What the installed archive still needs from outside itself.
105
+ #
106
+ # cmake/Bundler.cmake archives STATIC_LIBRARY dependencies and nothing else, and an IMPORTED target
107
+ # carries no link interface of its own, so every dependency resolved as a shared library stays
108
+ # outside the archive. Publishing them here is what stops a consumer linking it from hitting
109
+ # unresolved symbols.
110
+ #
111
+ # Which ones those are is a property of the configuration, not a fixed list. The packaging
112
+ # configuration bundles everything and needs only the platform libraries -- which is also what
113
+ # cbc's own link line carries -- while an install built against the platform's gRPC or OpenSSL
114
+ # needs those named too. The package targets are therefore taken from the graph below; only the
115
+ # platform libraries, which are not targets at all, stay conditional on the platform.
116
+ set(_static_deps "find_dependency(Threads)")
117
+ set(_static_libs "Threads::Threads")
118
+ # Threads::Threads carries the platform's thread flag; pkg-config has no equivalent, so the flag
119
+ # itself goes into Libs.private. It is empty where pthread lives in libc, which is every platform
120
+ # this currently builds on except EL8, where it is -lpthread.
121
+ set(_static_pc "${CMAKE_THREAD_LIBS_INIT}")
122
+
123
+ # Which package targets to name is decided by the link graph, not by re-deriving the option
124
+ # combinations that produced it.
125
+ #
126
+ # Five review rounds were spent adding one more entry to a hand-written list, and a sixth found
127
+ # that zlib reaches the archive through OpenSSL's interface as well as through gRPC -- so a
128
+ # condition of "couchbase2 is on" was wrong in a configuration nobody had considered.
129
+ # cmake/Bundler.cmake already walks the graph to decide what to archive; what it declined to
130
+ # archive is exactly what has to be named here, so that list is the input.
131
+ #
132
+ # The mapping from a target to the find_dependency that recreates it stays explicit, because it is
133
+ # not mechanical: the package providing protobuf::libprotobuf is called Protobuf, the version
134
+ # floor is the one cmake/GrpcProtobuf.cmake enforces, and the pkg-config fallback in
135
+ # cmake/OpenSSL.cmake has no find_dependency form at all.
136
+ get_property(_bundle_external GLOBAL PROPERTY couchbase_cxx_client_static_EXTERNAL_LIBS)
137
+ get_property(_bundle_opts GLOBAL PROPERTY couchbase_cxx_client_static_EXTERNAL_OPTS)
138
+
139
+ if("ZLIB::ZLIB" IN_LIST _bundle_external)
140
+ string(APPEND _static_deps "\nfind_dependency(ZLIB)")
141
+ list(APPEND _static_libs "ZLIB::ZLIB")
142
+ string(APPEND _static_pc " -lz")
143
+ endif()
144
+
145
+ # Without COUCHBASE_CXX_CLIENT_STATIC_BORINGSSL the client links the platform's OpenSSL, PUBLIC and
146
+ # shared. BoringSSL itself is a pair of STATIC_LIBRARY targets and is archived, so it needs nothing
147
+ # here, and COUCHBASE_CXX_CLIENT_POST_LINKED_OPENSSL links no TLS at all -- both of which the graph
148
+ # states directly rather than by inference.
149
+ #
150
+ # cmake/OpenSSL.cmake falls back to pkg-config when CMake's own OpenSSL targets are unusable, and
151
+ # the client target in CMakeLists.txt then links PkgConfig::PKG_CONFIG_OPENSSL. Exporting
152
+ # find_dependency(OpenSSL) in that case would hand the consumer back exactly the targets the build
153
+ # rejected, so the fallback is exported as the fallback.
154
+ set(_static_pc_requires)
155
+ if("PkgConfig::PKG_CONFIG_OPENSSL" IN_LIST _bundle_external)
156
+ # The same module the build resolved, not "openssl": on a host where only openssl11 exists --
157
+ # which is the reason this fallback is taken at all -- asking for the wrong one either fails or
158
+ # silently selects a different TLS installation than the archive was compiled against.
159
+ string(
160
+ APPEND
161
+ _static_deps
162
+ "\nfind_dependency(PkgConfig)\npkg_check_modules(PKG_CONFIG_OPENSSL REQUIRED IMPORTED_TARGET ${COUCHBASE_CXX_CLIENT_OPENSSL_PKGCONFIG_MODULE})"
163
+ )
164
+ list(APPEND _static_libs "PkgConfig::PKG_CONFIG_OPENSSL")
165
+ # Requires.private rather than -lssl -lcrypto, so pkg-config resolves the module and carries its
166
+ # library directories and flags across; flattening it to two names drops both.
167
+ list(APPEND _static_pc_requires "${COUCHBASE_CXX_CLIENT_OPENSSL_PKGCONFIG_MODULE}")
168
+ elseif("OpenSSL::SSL" IN_LIST _bundle_external OR "OpenSSL::Crypto" IN_LIST _bundle_external)
169
+ string(APPEND _static_deps "\nfind_dependency(OpenSSL)")
170
+ list(APPEND _static_libs "OpenSSL::SSL" "OpenSSL::Crypto")
171
+ string(APPEND _static_pc " -lssl -lcrypto")
172
+ endif()
173
+
174
+ # The generated stubs are archived; the gRPC and Protobuf they call are not, whenever
175
+ # cmake/GrpcProtobuf.cmake resolved them from the platform. Keyed on the graph, this is
176
+ # automatically silent when gRPC was resolved only for the FIT performer, which is a separate
177
+ # executable and puts nothing in this archive.
178
+ if("gRPC::grpc++" IN_LIST _bundle_external OR "grpc++" IN_LIST _bundle_external)
179
+ string(APPEND _static_deps "\nfind_dependency(gRPC)\nfind_dependency(Protobuf 3.15)")
180
+ list(APPEND _static_libs "gRPC::grpc++" "protobuf::libprotobuf")
181
+ string(APPEND _static_pc " -lgrpc++ -lgrpc -lprotobuf")
182
+ endif()
183
+
184
+ # Every plain link item the graph carries: Windows import libraries (iphlpapi for GetNetworkParams,
185
+ # bcrypt for the BCrypt* calls in core/crypto, ws2_32 and crypt32 from a source-built gRPC),
186
+ # libexecinfo where backtrace() is not in libc, and whatever else a subdirectory contributed.
187
+ #
188
+ # Taken from the graph rather than written out per platform, because the hand-written version was
189
+ # wrong in a new way every round -- keyed on MINGW when MSVC needed it too, or simply missing an
190
+ # entry contributed somewhere nobody thought to look.
191
+ #
192
+ # Published by NAME: cmake/CompilerOptions.cmake and gRPC both contribute find_library results, and
193
+ # an absolute path from the build host means nothing on a consumer's machine.
194
+ foreach(_ext IN LISTS _bundle_external)
195
+ if(TARGET ${_ext})
196
+ continue()
197
+ endif()
198
+ get_filename_component(_ext_name "${_ext}" NAME_WE)
199
+ string(REGEX REPLACE "^lib" "" _ext_name "${_ext_name}")
200
+ string(REGEX REPLACE "^-l" "" _ext_name "${_ext_name}")
201
+ if(_ext_name AND NOT _ext_name IN_LIST _static_libs)
202
+ list(APPEND _static_libs "${_ext_name}")
203
+ string(APPEND _static_pc " -l${_ext_name}")
204
+ endif()
205
+ endforeach()
206
+
207
+ # bcrypt cannot be taken from the graph. core/crypto/cbcrypto.cc calls BCryptOpenAlgorithmProvider
208
+ # under MSVC, but it is compiled straight into the client from the source list -- the
209
+ # core/crypto/CMakeLists.txt that links bcrypt.lib is never added by any add_subdirectory, so that
210
+ # link never happens. Whether bcrypt reaches the graph at all therefore depends on some other
211
+ # dependency happening to pull it in, which is not something to leave a shipped package resting on.
212
+ if(WIN32 AND NOT bcrypt IN_LIST _static_libs)
213
+ list(APPEND _static_libs bcrypt)
214
+ string(APPEND _static_pc " -lbcrypt")
215
+ endif()
216
+
217
+ # The three below are not in the graph as link items on every platform -- libc supplies them and
218
+ # the toolchain adds them implicitly -- but a consumer linking a bare archive gets no such help.
219
+ # Deduplicated against the graph above, so naming one twice costs nothing while missing one breaks
220
+ # the package.
221
+ if(CMAKE_DL_LIBS AND NOT CMAKE_DL_LIBS IN_LIST _static_libs)
222
+ list(APPEND _static_libs "${CMAKE_DL_LIBS}")
223
+ string(APPEND _static_pc " -l${CMAKE_DL_LIBS}")
224
+ endif()
225
+ if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
226
+ foreach(_libc_extra m rt)
227
+ if(NOT _libc_extra IN_LIST _static_libs)
228
+ list(APPEND _static_libs ${_libc_extra})
229
+ string(APPEND _static_pc " -l${_libc_extra}")
230
+ endif()
231
+ endforeach()
232
+ endif()
233
+
234
+ # Audit everything published above against the whole graph the bundler walked.
235
+ #
236
+ # The package targets come from that graph, but the platform libraries above are still written by
237
+ # hand, and that half is where the misses were: bcrypt from core/crypto, iphlpapi from the client
238
+ # target, libexecinfo from CompilerOptions -- each contributed by a subdirectory nobody thought to
239
+ # enumerate, and each found by a reviewer rather than by the build. This closes that loop:
240
+ # cmake/Bundler.cmake records every link item it did NOT archive, and anything unrepresented is
241
+ # reported at configure time.
242
+ #
243
+ # A warning, not an error: the mapping from a link item to the name a consumer needs is not always
244
+ # one to one -- a namespaced target and its find_dependency package differ (protobuf::libprotobuf
245
+ # comes from Protobuf), and header-only interface targets contribute nothing to link. Judgement
246
+ # belongs to whoever reads it, so this reports and does not guess.
247
+ # Reduce both sides to bare lowercase names, so a path, an -lfoo, a foo.lib and a namespaced
248
+ # target all compare alike. Compared as list members rather than by regex: a target name is not a
249
+ # pattern, and gRPC::grpc++ is not even a valid one.
250
+ set(_published_names)
251
+ foreach(_pub IN LISTS _static_libs)
252
+ string(REGEX REPLACE "^.*::" "" _pub "${_pub}")
253
+ string(TOLOWER "${_pub}" _pub)
254
+ list(APPEND _published_names "${_pub}")
255
+ endforeach()
256
+ string(REPLACE " " ";" _pc_items "${_static_pc}")
257
+ foreach(_pub IN LISTS _pc_items)
258
+ string(REGEX REPLACE "^-l" "" _pub "${_pub}")
259
+ string(TOLOWER "${_pub}" _pub)
260
+ list(APPEND _published_names "${_pub}")
261
+ endforeach()
262
+
263
+ set(_unrepresented)
264
+ foreach(_ext IN LISTS _bundle_external)
265
+ if(_ext MATCHES "::")
266
+ string(REGEX REPLACE "^.*::" "" _ext_name "${_ext}")
267
+ else()
268
+ get_filename_component(_ext_name "${_ext}" NAME_WE)
269
+ string(REGEX REPLACE "^lib" "" _ext_name "${_ext_name}")
270
+ string(REGEX REPLACE "^-l" "" _ext_name "${_ext_name}")
271
+ endif()
272
+ string(TOLOWER "${_ext_name}" _ext_name)
273
+ if(_ext_name AND NOT _ext_name IN_LIST _published_names)
274
+ list(APPEND _unrepresented "${_ext}")
275
+ endif()
276
+ endforeach()
277
+ if(_unrepresented)
278
+ message(
279
+ WARNING
280
+ "The installed static package does not name these dependencies, which cmake/Bundler.cmake "
281
+ "left outside the archive: ${_unrepresented}. A consumer linking "
282
+ "libcouchbase_cxx_client_static.a may get unresolved symbols from them. Add them in "
283
+ "cmake/Packaging.cmake, or record why they need no entry.")
284
+ endif()
285
+
286
+ # Link options the archive was built with, kept apart from the libraries because pkg-config wants
287
+ # them verbatim in Libs.private and CMake wants them as INTERFACE_LINK_OPTIONS. A sanitizer build
288
+ # is the case that matters: the objects carry references into the sanitizer runtime, and a
289
+ # consumer linking without the flag gets undefined symbols with no indication why.
290
+ list(JOIN _bundle_opts ";" couchbase_cxx_client_static_LINK_OPTIONS)
291
+ foreach(_opt IN LISTS _bundle_opts)
292
+ string(APPEND _static_pc " ${_opt}")
293
+ endforeach()
294
+
295
+ list(JOIN _static_pc_requires ", " couchbase_cxx_client_static_PC_REQUIRES_PRIVATE)
296
+
297
+ set(couchbase_cxx_client_static_FIND_DEPENDENCIES "${_static_deps}")
298
+ list(JOIN _static_libs ";" couchbase_cxx_client_static_LINK_LIBRARIES)
299
+ string(STRIP "${_static_pc}" couchbase_cxx_client_static_PC_LIBS_PRIVATE)
300
+
25
301
  configure_package_config_file(
26
302
  ${PROJECT_SOURCE_DIR}/cmake/couchbase_cxx_client_static-config.cmake.in
27
303
  ${PROJECT_BINARY_DIR}/couchbase_cxx_client_static-config.cmake
@@ -35,6 +311,30 @@ if(COUCHBASE_CXX_CLIENT_BUILD_STATIC)
35
311
  DESTINATION ${CMAKE_INSTALL_LIBDIR}/pkgconfig)
36
312
 
37
313
  install(FILES ${couchbase_cxx_client_static_IMPORTED_LOCATION} DESTINATION ${CMAKE_INSTALL_LIBDIR})
314
+
315
+ # This archive carries every vendored dependency, so its debug info dwarfs everything else the
316
+ # development package ships: 2.8 GB against the 126 MB of the same archive stripped. Most
317
+ # distributions strip static archives themselves -- EL through brp-strip-static-archive, Debian
318
+ # through dh_strip -- but Fedora no longer does, and there the development package went out at
319
+ # 332 MB where every other target ships 13 MB.
320
+ #
321
+ # Strip it here so what ships does not depend on which of those a distribution still runs. Only for
322
+ # a package build: a local install is where someone debugging into the vendored code wants the
323
+ # symbols, and stripping is a no-op on a distribution that has already done it.
324
+ if(COUCHBASE_CXX_CLIENT_PACKAGE_BUILD AND CMAKE_STRIP)
325
+ get_filename_component(_static_archive_name "${couchbase_cxx_client_static_IMPORTED_LOCATION}" NAME)
326
+ install(
327
+ CODE "
328
+ set(_archive \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${CMAKE_INSTALL_LIBDIR}/${_static_archive_name}\")
329
+ if(EXISTS \"\${_archive}\")
330
+ message(STATUS \"Stripping debug info from \${_archive}\")
331
+ execute_process(COMMAND \"${CMAKE_STRIP}\" --strip-debug \"\${_archive}\" RESULT_VARIABLE _strip_result)
332
+ if(NOT _strip_result EQUAL 0)
333
+ message(FATAL_ERROR \"Failed to strip \${_archive}: \${_strip_result}\")
334
+ endif()
335
+ endif()
336
+ ")
337
+ endif()
38
338
  endif()
39
339
 
40
340
  if(COUCHBASE_CXX_CLIENT_BUILD_SHARED)
@@ -79,6 +379,9 @@ endif()
79
379
  add_custom_command(
80
380
  OUTPUT ${COUCHBASE_CXX_CLIENT_MANIFEST}
81
381
  WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
382
+ # Fail loudly if this is not a git checkout (e.g. a bare jj workspace with no .git),
383
+ # instead of silently emitting an empty manifest and a broken empty tarball.
384
+ COMMAND ${CMAKE_COMMAND} -P ${PROJECT_SOURCE_DIR}/cmake/require-git-checkout.cmake
82
385
  COMMAND git ls-files --recurse-submodules | LC_ALL=C sort > ${COUCHBASE_CXX_CLIENT_MANIFEST})
83
386
 
84
387
  set(COUCHBASE_CXX_TARBALL_THIRD_PARTY_GLOB_FILE ${PROJECT_SOURCE_DIR}/cmake/tarball_glob.txt)
@@ -101,6 +404,7 @@ set(OTELCPP_PROTO_PATH \"\${PROJECT_SOURCE_DIR}/third_party_cache/opentelemetry/
101
404
  set(COUCHBASE_CXX_CLIENT_GIT_REVISION \"${COUCHBASE_CXX_CLIENT_GIT_REVISION}\")
102
405
  set(COUCHBASE_CXX_CLIENT_GIT_DESCRIBE \"${COUCHBASE_CXX_CLIENT_GIT_DESCRIBE}\")
103
406
  set(COUCHBASE_CXX_CLIENT_BUILD_TIMESTAMP \"${COUCHBASE_CXX_CLIENT_BUILD_TIMESTAMP}\")
407
+ set(COUCHBASE_CXX_CLIENT_SOURCE_DATE_EPOCH \"${COUCHBASE_CXX_CLIENT_SOURCE_DATE_EPOCH}\")
104
408
  set(COUCHBASE_CXX_CLIENT_EMBED_MOZILLA_CA_BUNDLE_ROOT \"\${PROJECT_SOURCE_DIR}/third_party_cache\" CACHE STRING \"\" FORCE)
105
409
  message(STATUS \"Building from Tarball: ${COUCHBASE_CXX_CLIENT_TARBALL_NAME}.tar.gz\")
106
410
  ")
@@ -120,15 +424,51 @@ add_custom_command(
120
424
  -DCOUCHBASE_CXX_CLIENT_EMBED_MOZILLA_CA_BUNDLE_ROOT="${PROJECT_BINARY_DIR}/packaging/${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/tmp/cache"
121
425
  -DCOUCHBASE_CXX_CLIENT_BUILD_TESTS=OFF -DCOUCHBASE_CXX_CLIENT_BUILD_TOOLS=ON -DCOUCHBASE_CXX_CLIENT_BUILD_DOCS=OFF
122
426
  -DCOUCHBASE_CXX_CLIENT_BUILD_OPENTELEMETRY=ON
427
+ # couchbase2:// pulls gRPC, protobuf, abseil, re2, c-ares and the Protostellar schema. This
428
+ # configure exists to populate third_party_cache, so it must enable every option any consumer of
429
+ # the tarball may build with -- an option left OFF here is a dependency missing from the cache,
430
+ # and a from-tarball build with it ON then reaches the network (or fails, when offline).
431
+ # PACKAGE_BUILD for the same reason: without it gRPC resolves from the platform's packages on a
432
+ # host that has them, and its sources never enter the cache the packages build from.
433
+ -DCOUCHBASE_CXX_CLIENT_BUILD_COUCHBASE2=ON -DCOUCHBASE_CXX_CLIENT_PACKAGE_BUILD=ON
123
434
  -DCOUCHBASE_CXX_CLIENT_STATIC_BORINGSSL=ON -DCPM_DOWNLOAD_ALL=ON -DCPM_USE_NAMED_CACHE_DIRECTORIES=ON
124
435
  -DCPM_USE_LOCAL_PACKAGES=OFF -DCOUCHBASE_CXX_CLIENT_BUILD_STATIC=ON -DCOUCHBASE_CXX_CLIENT_BUILD_SHARED=ON
125
436
  -DCOUCHBASE_CXX_CLIENT_INSTALL=ON -DCOUCHBASE_CXX_RECORD_BUILD_INFO_FOR_TARBALL=ON
437
+ # Pass the frozen instant explicitly: this inner configure runs at build time against a
438
+ # .git-less extracted copy, so without these it would fall back to wall-clock for an
439
+ # out-of-source build (build dir outside the worktree, where git cannot walk up to .git).
440
+ "-DCOUCHBASE_CXX_CLIENT_SOURCE_DATE_EPOCH=${COUCHBASE_CXX_CLIENT_SOURCE_DATE_EPOCH}"
441
+ "-DCOUCHBASE_CXX_CLIENT_BUILD_TIMESTAMP=${COUCHBASE_CXX_CLIENT_BUILD_TIMESTAMP}"
126
442
  COMMAND
127
- ${XARGS} -a ${COUCHBASE_CXX_TARBALL_THIRD_PARTY_GLOB_FILE} -I {} find
443
+ # -d: one pattern per line, with quote processing off. Without it an apostrophe anywhere in the
444
+ # glob file -- a comment is enough -- aborts xargs, and since its status is hidden by the pipe
445
+ # below, every pattern after that line is dropped from a tarball that still reports success.
446
+ # The argument has to reach xargs as backslash-n, which takes four backslashes here: CMake
447
+ # collapses them to two, and the shell that ninja runs the command in collapses those to one.
448
+ ${XARGS} -d "\\\\n" -a ${COUCHBASE_CXX_TARBALL_THIRD_PARTY_GLOB_FILE} -I {} find
128
449
  "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/tmp/cache" -wholename "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/tmp/cache/{}"
129
450
  -type f
130
451
  | grep -v
131
- -e "/benchmark"
452
+ -e "/third_party/benchmark/"
453
+ -e "/grpc/doc/"
454
+ -e "/grpc/examples/"
455
+ -e "/grpc/src/android"
456
+ -e "/grpc/src/csharp"
457
+ -e "/grpc/src/objective-c"
458
+ -e "/grpc/src/php"
459
+ -e "/grpc/src/python"
460
+ -e "/grpc/src/ruby"
461
+ -e "/grpc/test/.*\\.cc"
462
+ -e "/grpc/tools/"
463
+ -e "/protobuf/conformance"
464
+ -e "/protobuf/csharp"
465
+ -e "/protobuf/examples"
466
+ -e "/protobuf/java"
467
+ -e "/protobuf/objectivec"
468
+ -e "/protobuf/php"
469
+ -e "/protobuf/python"
470
+ -e "/protobuf/ruby"
471
+ -e "/protobuf/rust"
132
472
  -e "/opentelemetry.*/functional"
133
473
  -e "/opentelemetry.*/install"
134
474
  -e "/opentelemetry.*/test"
@@ -145,10 +485,11 @@ add_custom_command(
145
485
  -e "/opentelemetry/tools"
146
486
  -e "crypto_test_data"
147
487
  -e "googletest"
148
- | uniq >
488
+ | LC_ALL=C sort -u >
149
489
  "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/tmp/third_party_manifest.txt"
150
490
  COMMAND ${CMAKE_COMMAND} -E make_directory "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/tmp/filtered_cache"
151
- COMMAND ${XARGS} -a "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/tmp/third_party_manifest.txt" -I {} ${CP} --parents
491
+ COMMAND ${XARGS} -d "\\\\n" -a "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/tmp/third_party_manifest.txt" -I {} ${CP}
492
+ --parents
152
493
  {} "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/tmp/filtered_cache"
153
494
  COMMAND
154
495
  ${CMAKE_COMMAND} -E rename
@@ -160,7 +501,11 @@ add_custom_command(
160
501
  "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/third_party_cache/cpm/CPM_*.cmake"
161
502
  COMMAND ${CMAKE_COMMAND} -E rm -rf "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}/tmp"
162
503
  # https://reproducible-builds.org/docs/archives/
163
- COMMAND ${TAR} --sort=name --mtime="${COUCHBASE_CXX_CLIENT_BUILD_TIMESTAMP}Z" --owner=0 --group=0 --numeric-owner -czf
504
+ # --mtime=@<epoch>: timezone-free fixed mtime from the frozen SOURCE_DATE_EPOCH (not a tz-local
505
+ # string mislabelled with "Z"). --mode: normalize permission bits so the builder's umask does
506
+ # not leak into directory/file modes. gzip -n: keep the mtime/filename out of the gzip header.
507
+ COMMAND ${TAR} --sort=name "--mtime=@${COUCHBASE_CXX_CLIENT_SOURCE_DATE_EPOCH}" --owner=0 --group=0
508
+ --numeric-owner "--mode=go+u,go-w" "--use-compress-program=gzip -n" -cf
164
509
  "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}.tar.gz" "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}"
165
510
  COMMAND ${CMAKE_COMMAND} -E rm -rf "${COUCHBASE_CXX_CLIENT_TARBALL_NAME}"
166
511
  DEPENDS ${COUCHBASE_CXX_CLIENT_MANIFEST})
@@ -170,8 +515,21 @@ add_custom_target(packaging_tarball DEPENDS ${COUCHBASE_CXX_CLIENT_TARBALL})
170
515
  option(COUCHBASE_CXX_CLIENT_DEB_TARGETS "Enable targets for building DEBs" FALSE)
171
516
  if(COUCHBASE_CXX_CLIENT_DEB_TARGETS)
172
517
  find_program(DPKG_BUILDPACKAGE dpkg-buildpackage REQUIRED) # apt install -y dpkg-dev
173
- find_program(SUDO sudo REQUIRED) # apt install -y sudo
174
- find_program(COWBUILDER cowbuilder REQUIRED) # apt install -y cowbuilder
518
+ find_program(SBUILD sbuild REQUIRED) # apt install -y sbuild
519
+ find_program(MMDEBSTRAP mmdebstrap REQUIRED) # apt install -y mmdebstrap
520
+
521
+ # sbuild builds each distro inside a throwaway chroot that mmdebstrap creates rootlessly
522
+ # (unshare mode, no sudo required). mmdebstrap and sbuild expect the Debian host
523
+ # architecture (e.g. amd64, arm64), which differs from CMAKE_SYSTEM_PROCESSOR (x86_64,
524
+ # aarch64) that is used elsewhere for the human-readable result directory names.
525
+ execute_process(
526
+ COMMAND dpkg --print-architecture
527
+ RESULT_VARIABLE _dpkg_arch_result
528
+ OUTPUT_VARIABLE COUCHBASE_CXX_CLIENT_DEB_HOST_ARCH
529
+ OUTPUT_STRIP_TRAILING_WHITESPACE)
530
+ if(NOT _dpkg_arch_result EQUAL 0 OR NOT COUCHBASE_CXX_CLIENT_DEB_HOST_ARCH)
531
+ message(FATAL_ERROR "Failed to determine the Debian host architecture via 'dpkg --print-architecture'")
532
+ endif()
175
533
 
176
534
  string(TIMESTAMP COUCHBASE_CXX_CLIENT_DEB_DATE "%a, %d %b %Y %H:%M:%S %z" UTC)
177
535
 
@@ -207,53 +565,75 @@ if(COUCHBASE_CXX_CLIENT_DEB_TARGETS)
207
565
  add_custom_command(
208
566
  OUTPUT ${COUCHBASE_CXX_CLIENT_DEBIAN_DSC}
209
567
  WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/packaging/workspace"
210
- COMMAND ${DPKG_BUILDPACKAGE} -us -uc
568
+ # Build the source package only (-S) and skip the host build-dependency check (-d): the
569
+ # actual compilation happens inside the sbuild chroot, so the host needs only dpkg-dev.
570
+ COMMAND ${DPKG_BUILDPACKAGE} -S -us -uc -d
211
571
  DEPENDS ${COUCHBASE_CXX_CLIENT_DEBIAN_ORIG_TARBALL} ${COUCHBASE_CXX_CLIENT_DEBIAN_TARBALL_EXTRACTED})
212
572
 
213
- function(select_mirror_options distro options)
214
- if(${distro} STREQUAL "bookworm" OR ${distro} STREQUAL "trixie")
215
- set(${options}
216
- --components
217
- main
218
- --mirror
219
- https://ftp.debian.org/debian
220
- PARENT_SCOPE)
573
+ # Per-distribution apt source used to bootstrap the build chroot: the mirror, the keyring
574
+ # that verifies it, the package that installs that keyring inside the chroot (so the
575
+ # sources.list signed-by reference resolves), and the components to enable.
576
+ function(select_apt_source distro out_mirror out_keyring out_keyring_pkg out_components)
577
+ if("${distro}" STREQUAL "kali-rolling")
578
+ set(${out_mirror} "http://http.kali.org/kali" PARENT_SCOPE)
579
+ set(${out_keyring} "/usr/share/keyrings/kali-archive-keyring.gpg" PARENT_SCOPE)
580
+ set(${out_keyring_pkg} "kali-archive-keyring" PARENT_SCOPE)
581
+ set(${out_components} "main" PARENT_SCOPE)
582
+ elseif("${distro}" STREQUAL "bookworm" OR "${distro}" STREQUAL "trixie")
583
+ # http (not https): the --variant=buildd chroot has no ca-certificates, so in-chroot apt over
584
+ # TLS would fail; apt authenticates packages by GPG signature regardless of transport.
585
+ set(${out_mirror} "http://deb.debian.org/debian" PARENT_SCOPE)
586
+ set(${out_keyring} "/usr/share/keyrings/debian-archive-keyring.gpg" PARENT_SCOPE)
587
+ set(${out_keyring_pkg} "debian-archive-keyring" PARENT_SCOPE)
588
+ set(${out_components} "main" PARENT_SCOPE)
589
+ elseif("${CMAKE_SYSTEM_PROCESSOR}" STREQUAL "aarch64")
590
+ set(${out_mirror} "http://ports.ubuntu.com/ubuntu-ports" PARENT_SCOPE)
591
+ set(${out_keyring} "/usr/share/keyrings/ubuntu-archive-keyring.gpg" PARENT_SCOPE)
592
+ set(${out_keyring_pkg} "ubuntu-keyring" PARENT_SCOPE)
593
+ set(${out_components} "main universe" PARENT_SCOPE)
221
594
  else()
222
- if(${CMAKE_SYSTEM_PROCESSOR} STREQUAL "aarch64")
223
- set(${options}
224
- --components
225
- "main universe"
226
- --mirror
227
- http://ports.ubuntu.com/ubuntu-ports
228
- PARENT_SCOPE)
229
- else()
230
- set(${options}
231
- --components
232
- "main universe"
233
- --mirror
234
- http://archive.ubuntu.com/ubuntu
235
- PARENT_SCOPE)
236
- endif()
595
+ set(${out_mirror} "http://archive.ubuntu.com/ubuntu" PARENT_SCOPE)
596
+ set(${out_keyring} "/usr/share/keyrings/ubuntu-archive-keyring.gpg" PARENT_SCOPE)
597
+ set(${out_keyring_pkg} "ubuntu-keyring" PARENT_SCOPE)
598
+ set(${out_components} "main universe" PARENT_SCOPE)
237
599
  endif()
238
600
  endfunction()
239
601
 
240
- set(cowbuilder_results "${PROJECT_BINARY_DIR}/packaging/results")
241
- file(MAKE_DIRECTORY "${cowbuilder_results}")
602
+ set(COUCHBASE_CXX_CLIENT_SUPPORTED_DISTROS
603
+ "jammy"
604
+ "noble"
605
+ "resolute"
606
+ "bookworm"
607
+ "trixie"
608
+ "kali-rolling"
609
+ CACHE STRING "Semicolon-separated list of distributions to build DEB packages for")
610
+
611
+ message(STATUS "Supported distributions for DEB packages: ${COUCHBASE_CXX_CLIENT_SUPPORTED_DISTROS}")
242
612
 
243
- list(
244
- APPEND
245
- COUCHBASE_CXX_CLIENT_SUPPORTED_DISTROS
246
- "jammy"
247
- "noble"
248
- "bookworm"
249
- "trixie")
613
+ set(sbuild_results "${PROJECT_BINARY_DIR}/packaging/results")
614
+ set(sbuild_chroots "${PROJECT_BINARY_DIR}/packaging/chroots")
615
+ file(MAKE_DIRECTORY "${sbuild_results}")
616
+ file(MAKE_DIRECTORY "${sbuild_chroots}")
250
617
 
251
- set(pbuilder_root "${PROJECT_BINARY_DIR}/packaging/base.cow")
252
- set(cowbuilder_root "${PROJECT_BINARY_DIR}/packaging/root.cow")
618
+ # Build the distros one at a time (chained through last_output) so several full SDK
619
+ # compilations do not hammer a single machine simultaneously.
253
620
  set(last_output "")
254
621
  foreach(distro ${COUCHBASE_CXX_CLIENT_SUPPORTED_DISTROS})
255
- select_mirror_options(${distro} mirror_options)
622
+ if(distro STREQUAL "")
623
+ continue() # tolerate a trailing ';' or empty entry in the overridable distro list
624
+ endif()
625
+ select_apt_source("${distro}" mirror keyring keyring_pkg components)
626
+ # mmdebstrap verifies the bootstrap against this keyring, which must exist on the build host.
627
+ # Fail early with an actionable message instead of a cryptic mmdebstrap error mid-build.
628
+ if(NOT EXISTS "${keyring}")
629
+ message(FATAL_ERROR "Keyring ${keyring} needed to build '${distro}' DEBs is missing; "
630
+ "install the '${keyring_pkg}' package on the build host.")
631
+ endif()
256
632
  set(timestamp "${PROJECT_BINARY_DIR}/packaging/${distro}_done.txt")
633
+ set(chroot_tarball "${sbuild_chroots}/${distro}-${COUCHBASE_CXX_CLIENT_DEB_HOST_ARCH}.tar.zst")
634
+ set(distro_results
635
+ "${sbuild_results}/couchbase-cxx-client-${COUCHBASE_CXX_CLIENT_PACKAGE_VERSION}-${COUCHBASE_CXX_CLIENT_PACKAGE_RELEASE}.${distro}.${CMAKE_SYSTEM_PROCESSOR}"
636
+ )
257
637
  set(dependencies ${COUCHBASE_CXX_CLIENT_DEBIAN_DSC})
258
638
 
259
639
  if(last_output)
@@ -264,13 +644,15 @@ if(COUCHBASE_CXX_CLIENT_DEB_TARGETS)
264
644
  COMMENT "Building DEB for ${distro}"
265
645
  OUTPUT ${timestamp}
266
646
  WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/packaging"
267
- COMMAND ${SUDO} ${CMAKE_COMMAND} -E rm -rf "${cowbuilder_root}"
268
- COMMAND ${SUDO} ${COWBUILDER} --create --buildplace "${pbuilder_root}" --basepath "${cowbuilder_root}"
269
- --distribution ${distro} ${mirror_options}
647
+ COMMAND ${CMAKE_COMMAND} -E make_directory "${distro_results}" "${sbuild_chroots}"
648
+ COMMAND ${CMAKE_COMMAND} -E rm -f "${chroot_tarball}"
649
+ COMMAND ${MMDEBSTRAP} --variant=buildd --arch=${COUCHBASE_CXX_CLIENT_DEB_HOST_ARCH}
650
+ "--include=${keyring_pkg}" "${distro}" "${chroot_tarball}"
651
+ "deb [signed-by=${keyring}] ${mirror} ${distro} ${components}"
270
652
  COMMAND
271
- ${SUDO} ${COWBUILDER} --build --buildplace "${pbuilder_root}" --basepath "${cowbuilder_root}" --buildresult
272
- "${cowbuilder_results}/couchbase-cxx-client-${COUCHBASE_CXX_CLIENT_PACKAGE_VERSION}-${COUCHBASE_CXX_CLIENT_PACKAGE_RELEASE}.${distro}.${CMAKE_SYSTEM_PROCESSOR}"
273
- --debbuildopts -j8 --debbuildopts "-us -uc" ${COUCHBASE_CXX_CLIENT_DEBIAN_DSC}
653
+ ${SBUILD} --chroot-mode=unshare --dist=${distro} --arch=${COUCHBASE_CXX_CLIENT_DEB_HOST_ARCH}
654
+ "--chroot=${chroot_tarball}" "--build-dir=${distro_results}" --no-run-lintian --no-run-piuparts
655
+ --no-run-autopkgtest -j8 "${COUCHBASE_CXX_CLIENT_DEBIAN_DSC}"
274
656
  COMMAND touch ${timestamp}
275
657
  DEPENDS ${dependencies})
276
658
 
@@ -282,9 +664,49 @@ endif()
282
664
 
283
665
  option(COUCHBASE_CXX_CLIENT_RPM_TARGETS "Enable targets for building RPMs" FALSE)
284
666
  if(COUCHBASE_CXX_CLIENT_RPM_TARGETS)
285
- find_program(MOCK mock REQUIRED) # dnf install -y mock
286
667
  find_program(SPECTOOL spectool REQUIRED) # dnf install -y rpmdevtools
287
668
 
669
+ option(COUCHBASE_CXX_CLIENT_RPM_ROOTLESS
670
+ "Build RPMs by running mock inside a rootless podman container (no mock group/sudo on the host)"
671
+ OFF)
672
+ option(COUCHBASE_CXX_CLIENT_RPM_ROOTLESS_BOOTSTRAP_IMAGE
673
+ "Use mock's podman bootstrap image (needed for cross-distro roots; requires nested podman)"
674
+ OFF)
675
+ if(COUCHBASE_CXX_CLIENT_RPM_ROOTLESS)
676
+ find_program(PODMAN podman REQUIRED) # dnf install -y podman
677
+ # Fail early (like the DEB keyring check) if podman is not usable rootless.
678
+ execute_process(
679
+ COMMAND ${PODMAN} info --format "{{.Host.Security.Rootless}}"
680
+ RESULT_VARIABLE _podman_info_result
681
+ OUTPUT_VARIABLE _podman_rootless
682
+ OUTPUT_STRIP_TRAILING_WHITESPACE
683
+ ERROR_VARIABLE _podman_info_error)
684
+ if(NOT _podman_info_result EQUAL 0 OR NOT "${_podman_rootless}" STREQUAL "true")
685
+ message(FATAL_ERROR
686
+ "COUCHBASE_CXX_CLIENT_RPM_ROOTLESS=ON requires a working rootless podman "
687
+ "('podman info' must report Host.Security.Rootless=true). "
688
+ "Install podman and configure /etc/subuid and /etc/subgid for your user, or set the toggle OFF.\n"
689
+ "podman reported: ${_podman_info_error}")
690
+ endif()
691
+ set(COUCHBASE_CXX_CLIENT_RPM_BUILDER_BASE "registry.fedoraproject.org/fedora:44"
692
+ CACHE STRING "Base image for the rootless RPM builder (pin by digest for reproducibility)")
693
+ set(COUCHBASE_CXX_CLIENT_RPM_BUILDER_IMAGE "localhost/cxxcbc-rpm-builder:fedora-44"
694
+ CACHE STRING "Tag of the locally built rootless RPM builder image")
695
+ set(COUCHBASE_CXX_CLIENT_RPM_BUILDER_STAMP "${PROJECT_BINARY_DIR}/packaging/rpm-builder-image.stamp")
696
+ add_custom_command(
697
+ OUTPUT ${COUCHBASE_CXX_CLIENT_RPM_BUILDER_STAMP}
698
+ COMMAND ${PODMAN} build --build-arg "BASE=${COUCHBASE_CXX_CLIENT_RPM_BUILDER_BASE}"
699
+ -t ${COUCHBASE_CXX_CLIENT_RPM_BUILDER_IMAGE}
700
+ -f ${PROJECT_SOURCE_DIR}/cmake/rpm/Containerfile ${PROJECT_SOURCE_DIR}/cmake/rpm
701
+ COMMAND ${CMAKE_COMMAND} -E touch ${COUCHBASE_CXX_CLIENT_RPM_BUILDER_STAMP}
702
+ DEPENDS ${PROJECT_SOURCE_DIR}/cmake/rpm/Containerfile
703
+ COMMENT "Building rootless RPM builder image ${COUCHBASE_CXX_CLIENT_RPM_BUILDER_IMAGE}")
704
+ else()
705
+ # Only the non-rootless path runs mock on the host; the rootless path runs it inside the
706
+ # builder container, so a host mock is not required there.
707
+ find_program(MOCK mock REQUIRED) # dnf install -y mock
708
+ endif()
709
+
288
710
  string(TIMESTAMP COUCHBASE_CXX_CLIENT_RPM_DATE "%a %b %d %Y" UTC)
289
711
 
290
712
  set(COUCHBASE_CXX_CLIENT_SPEC "${PROJECT_BINARY_DIR}/packaging/couchbase-cxx-client.spec")
@@ -295,27 +717,53 @@ if(COUCHBASE_CXX_CLIENT_RPM_TARGETS)
295
717
  "couchbase-cxx-client-${COUCHBASE_CXX_CLIENT_PACKAGE_VERSION}-${COUCHBASE_CXX_CLIENT_PACKAGE_RELEASE}")
296
718
  set(COUCHBASE_CXX_CLIENT_SRPM "${PROJECT_BINARY_DIR}/packaging/srpm/${COUCHBASE_CXX_CLIENT_RPM_NAME}.el9.src.rpm")
297
719
 
720
+ # mock_launcher(<out_var> <resultdir>): expands to the command prefix used to run mock,
721
+ # either directly on the host (default) or inside a rootless podman container. The wrapper
722
+ # forwards all mock arguments unchanged, so the two paths are argument-compatible.
723
+ if(COUCHBASE_CXX_CLIENT_RPM_ROOTLESS AND COUCHBASE_CXX_CLIENT_RPM_ROOTLESS_BOOTSTRAP_IMAGE)
724
+ set(_rpm_use_boot 1)
725
+ else()
726
+ set(_rpm_use_boot 0)
727
+ endif()
728
+ macro(mock_launcher out_var resultdir)
729
+ if(COUCHBASE_CXX_CLIENT_RPM_ROOTLESS)
730
+ set(${out_var}
731
+ ${CMAKE_COMMAND} -E env
732
+ "RPM_PODMAN=${PODMAN}"
733
+ "RPM_BUILDER_IMAGE=${COUCHBASE_CXX_CLIENT_RPM_BUILDER_IMAGE}"
734
+ "RPM_PACKAGING_DIR=${PROJECT_BINARY_DIR}/packaging"
735
+ "MOCK_RESULTDIR=${resultdir}"
736
+ "SOURCE_DATE_EPOCH=${COUCHBASE_CXX_CLIENT_SOURCE_DATE_EPOCH}"
737
+ "MOCK_USE_BOOTSTRAP_IMAGE=${_rpm_use_boot}"
738
+ bash "${PROJECT_SOURCE_DIR}/cmake/rpm/mock-in-podman.sh")
739
+ else()
740
+ set(${out_var} ${MOCK})
741
+ endif()
742
+ endmacro()
743
+
744
+ mock_launcher(_srpm_mock "${PROJECT_BINARY_DIR}/packaging/srpm")
745
+ set(_srpm_extra_deps "")
746
+ if(COUCHBASE_CXX_CLIENT_RPM_ROOTLESS)
747
+ set(_srpm_extra_deps ${COUCHBASE_CXX_CLIENT_RPM_BUILDER_STAMP})
748
+ endif()
298
749
  add_custom_command(
299
750
  OUTPUT ${COUCHBASE_CXX_CLIENT_SRPM}
300
751
  WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/packaging"
301
752
  COMMAND ${SPECTOOL} --get-files couchbase-cxx-client.spec
302
- COMMAND ${MOCK} --buildsrpm --root=${COUCHBASE_CXX_CLIENT_DEFAULT_ROOT}
753
+ COMMAND ${_srpm_mock} --buildsrpm --root=${COUCHBASE_CXX_CLIENT_DEFAULT_ROOT}
303
754
  --resultdir=${PROJECT_BINARY_DIR}/packaging/srpm --spec couchbase-cxx-client.spec --sources .
304
- DEPENDS ${COUCHBASE_CXX_CLIENT_TARBALL} ${COUCHBASE_CXX_CLIENT_SPEC})
755
+ DEPENDS ${COUCHBASE_CXX_CLIENT_TARBALL} ${COUCHBASE_CXX_CLIENT_SPEC} ${_srpm_extra_deps})
305
756
 
306
757
  add_custom_target(packaging_srpm DEPENDS ${COUCHBASE_CXX_CLIENT_SRPM})
307
758
 
308
- list(
309
- APPEND
310
- COUCHBASE_CXX_CLIENT_SUPPORTED_ROOTS
311
- "opensuse-leap-15.6-${CMAKE_SYSTEM_PROCESSOR}"
312
- "rocky+epel-10-${CMAKE_SYSTEM_PROCESSOR}"
313
- "rocky+epel-9-${CMAKE_SYSTEM_PROCESSOR}"
314
- "rocky+epel-8-${CMAKE_SYSTEM_PROCESSOR}"
315
- "amazonlinux-2023-${CMAKE_SYSTEM_PROCESSOR}"
316
- "fedora-43-${CMAKE_SYSTEM_PROCESSOR}"
317
- "fedora-42-${CMAKE_SYSTEM_PROCESSOR}"
318
- "fedora-41-${CMAKE_SYSTEM_PROCESSOR}")
759
+ set(COUCHBASE_CXX_CLIENT_SUPPORTED_ROOTS
760
+ "rocky+epel-10-${CMAKE_SYSTEM_PROCESSOR}"
761
+ "rocky+epel-9-${CMAKE_SYSTEM_PROCESSOR}"
762
+ "rocky+epel-8-${CMAKE_SYSTEM_PROCESSOR}"
763
+ "amazonlinux-2023-${CMAKE_SYSTEM_PROCESSOR}"
764
+ "fedora-44-${CMAKE_SYSTEM_PROCESSOR}"
765
+ "fedora-43-${CMAKE_SYSTEM_PROCESSOR}"
766
+ CACHE STRING "Semicolon-separated list of mock roots to build RPM packages for")
319
767
 
320
768
  message(STATUS "Supported build roots for RPM packages: ${COUCHBASE_CXX_CLIENT_SUPPORTED_ROOTS}")
321
769
 
@@ -329,12 +777,16 @@ if(COUCHBASE_CXX_CLIENT_RPM_TARGETS)
329
777
  if(last_output)
330
778
  list(APPEND dependencies ${last_output})
331
779
  endif()
780
+ if(COUCHBASE_CXX_CLIENT_RPM_ROOTLESS)
781
+ list(APPEND dependencies ${COUCHBASE_CXX_CLIENT_RPM_BUILDER_STAMP})
782
+ endif()
332
783
 
784
+ mock_launcher(_root_mock "${PROJECT_BINARY_DIR}/packaging/rpm/${root}")
333
785
  add_custom_command(
334
786
  COMMENT "Building RPM for ${root}"
335
787
  OUTPUT ${timestamp}
336
788
  WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/packaging"
337
- COMMAND ${MOCK} --rebuild --root=${root} --resultdir=${PROJECT_BINARY_DIR}/packaging/rpm/${root}
789
+ COMMAND ${_root_mock} --rebuild --root=${root} --resultdir=${PROJECT_BINARY_DIR}/packaging/rpm/${root}
338
790
  "${COUCHBASE_CXX_CLIENT_SRPM}"
339
791
  COMMAND touch ${timestamp}
340
792
  DEPENDS ${dependencies})
@@ -399,7 +851,9 @@ if(COUCHBASE_CXX_CLIENT_APK_TARGETS)
399
851
  add_custom_command(
400
852
  OUTPUT ${cxxcbc_apkbuild_timestamp}
401
853
  WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/packaging"
402
- COMMAND ${ABUILD} -r
854
+ # abuild (unlike dpkg/rpm) does not derive SOURCE_DATE_EPOCH from any metadata, so pass the
855
+ # frozen epoch explicitly to clamp .apk mtimes for reproducibility.
856
+ COMMAND ${CMAKE_COMMAND} -E env SOURCE_DATE_EPOCH=${COUCHBASE_CXX_CLIENT_SOURCE_DATE_EPOCH} ${ABUILD} -r
403
857
  COMMAND touch ${cxxcbc_apkbuild_timestamp}
404
858
  DEPENDS ${COUCHBASE_CXX_CLIENT_TARBALL_ALPINE} ${cxxcbc_apkbuild_checksum})
405
859