├── .github ├── CODEOWNERS ├── PULL_REQUEST_TEMPLATE.md ├── release-drafter.yml └── workflows │ ├── ci-auth-checks.yml │ ├── ci-bookie-checks.yml │ ├── ci-checks.yml │ ├── ci-functions-checks.yml │ ├── ci-install-script-checks.yml │ ├── ci-packages-checks.yml │ ├── ci-release-checks.yml │ ├── ci-style-checks.yml │ ├── ci-trivy.yml │ ├── documentbot.yml │ └── release-note.yml ├── .gitignore ├── .header ├── CONTRIBUTING.md ├── LICENSE ├── Makefile ├── README.md ├── VERSION ├── docker └── amd64-linux.Dockerfile ├── docs ├── en │ ├── developer-guide.md │ ├── enable_completion.md │ ├── how-to-extend-pulsarctl-with-plugins.md │ ├── how-to-use-context.md │ ├── overview_of_pulsarctl.md │ └── release_process.md └── zh │ └── developer-guide.md ├── go.mod ├── go.sum ├── golangci.yml ├── install.sh ├── license_test.go ├── main.go ├── pkg ├── bkctl │ ├── autorecovery │ │ ├── autorecovery.go │ │ ├── decommission.go │ │ ├── decommission_test.go │ │ ├── get_lost_bookie_recovery_delay.go │ │ ├── list_under_replicated_ledger.go │ │ ├── lost_bookie_recovery_delay_test.go │ │ ├── recover_bookie.go │ │ ├── recover_bookie_test.go │ │ ├── set_lost_bookie_recovery_delay.go │ │ ├── set_lost_bookie_recovery_delay_test.go │ │ ├── test_help.go │ │ ├── trigger_audit.go │ │ ├── trigger_audit_test.go │ │ ├── who_is_auditor.go │ │ └── who_is_auditor_test.go │ ├── bk.go │ ├── bookie │ │ ├── bookie.go │ │ ├── expand_storage.go │ │ ├── expand_storage_test.go │ │ ├── gc.go │ │ ├── gc_details.go │ │ ├── gc_details_test.go │ │ ├── gc_status.go │ │ ├── gc_status_test.go │ │ ├── gc_test.go │ │ ├── last_log_mark.go │ │ ├── last_log_mark_test.go │ │ ├── list_disk_file.go │ │ ├── list_disk_file_test.go │ │ ├── set_readonly_state.go │ │ ├── set_readonly_state_test.go │ │ ├── state.go │ │ ├── state_test.go │ │ └── test_help.go │ ├── bookies │ │ ├── bookies.go │ │ ├── disk_usage_info.go │ │ ├── disk_usage_info_test.go │ │ ├── list.go │ │ ├── list_test.go │ │ └── test_help.go │ └── ledger │ │ ├── delete.go │ │ ├── delete_test.go │ │ ├── errors.go │ │ ├── get.go │ │ ├── get_test.go │ │ ├── ledger.go │ │ ├── list.go │ │ ├── list_test.go │ │ ├── read.go │ │ ├── read_test.go │ │ └── test_help.go ├── bookkeeper │ ├── admin.go │ ├── admin_config.go │ ├── autorecovery.go │ ├── bkdata │ │ ├── api_version.go │ │ ├── autorecovery_data.go │ │ ├── bookie_data.go │ │ ├── bookie_type.go │ │ ├── bookie_type_test.go │ │ ├── file_type.go │ │ ├── file_type_test.go │ │ └── ledger_metadata.go │ ├── bookie.go │ ├── bookies.go │ └── ledger.go ├── cmdutils │ ├── cmdutils.go │ ├── config.go │ ├── ctx_conf.go │ ├── descriptions.go │ ├── descriptions_test.go │ ├── group.go │ ├── output.go │ ├── output_test.go │ ├── token.go │ ├── token_test.go │ ├── verb.go │ └── version.go ├── ctl │ ├── brokers │ │ ├── broker.go │ │ ├── config.go │ │ ├── config_test.go │ │ ├── delete_dynamic_config.go │ │ ├── delete_dynamic_config_test.go │ │ ├── get_all_dynamic_config.go │ │ ├── get_runtime_config.go │ │ ├── healthcheck.go │ │ ├── healthcheck_test.go │ │ ├── list.go │ │ ├── list_dynamic_config.go │ │ ├── list_dynamic_config_test.go │ │ ├── list_test.go │ │ ├── namespaces.go │ │ ├── namespaces_test.go │ │ ├── test_help.go │ │ ├── update_dynamic_config.go │ │ └── update_dynamic_config_test.go │ ├── brokerstats │ │ ├── allocator_stats.go │ │ ├── allocator_stats_test.go │ │ ├── broker_stats.go │ │ ├── load_report.go │ │ ├── load_report_test.go │ │ ├── mbeans.go │ │ ├── mbeans_test.go │ │ ├── monitoring_metrics.go │ │ ├── monitoring_metrics_test.go │ │ ├── test_help.go │ │ └── topics.go │ ├── cluster │ │ ├── cluster.go │ │ ├── create.go │ │ ├── create_failure_domain.go │ │ ├── create_failure_domain_test.go │ │ ├── delete.go │ │ ├── delete_failure_domain.go │ │ ├── delete_failure_domain_test.go │ │ ├── delete_test.go │ │ ├── get.go │ │ ├── get_failure_domain.go │ │ ├── get_failure_domain_test.go │ │ ├── get_peer_clusters.go │ │ ├── get_peer_clusters_test.go │ │ ├── get_test.go │ │ ├── list.go │ │ ├── list_failure_domain.go │ │ ├── list_failure_domain_test.go │ │ ├── test.go │ │ ├── tls_test.go │ │ ├── update.go │ │ ├── update_failure_domain.go │ │ ├── update_failure_domain_test.go │ │ ├── update_peer_clusters.go │ │ ├── update_peer_clusters_test.go │ │ └── update_test.go │ ├── completion │ │ └── completion.go │ ├── context │ │ ├── context.go │ │ ├── create_context.go │ │ ├── create_context_test.go │ │ ├── current_context.go │ │ ├── current_context_test.go │ │ ├── delete_context.go │ │ ├── delete_context_test.go │ │ ├── get_contexts.go │ │ ├── internal │ │ │ ├── client_config.go │ │ │ ├── config_access.go │ │ │ └── loader.go │ │ ├── rename_context.go │ │ ├── rename_context_test.go │ │ ├── test_help.go │ │ └── use_context.go │ ├── functions │ │ ├── create.go │ │ ├── create_test.go │ │ ├── delete.go │ │ ├── delete_test.go │ │ ├── download.go │ │ ├── download_test.go │ │ ├── functions.go │ │ ├── get.go │ │ ├── get_test.go │ │ ├── list.go │ │ ├── list_test.go │ │ ├── putstate.go │ │ ├── putstate_test.go │ │ ├── querystate.go │ │ ├── restart.go │ │ ├── restart_test.go │ │ ├── start.go │ │ ├── start_test.go │ │ ├── stats.go │ │ ├── stats_test.go │ │ ├── status.go │ │ ├── status_test.go │ │ ├── stop.go │ │ ├── stop_test.go │ │ ├── test_help.go │ │ ├── trigger.go │ │ ├── trigger_test.go │ │ ├── update.go │ │ ├── update_test.go │ │ ├── upload.go │ │ ├── upload_test.go │ │ ├── util.go │ │ └── util_test.go │ ├── functionsworker │ │ ├── function_stats.go │ │ ├── functions_worker.go │ │ ├── functions_worker_test.go │ │ ├── get_cluster.go │ │ ├── get_cluster_leader.go │ │ ├── get_function_assignments.go │ │ ├── monitoring_metrics.go │ │ └── test_help.go │ ├── namespace │ │ ├── backlog_quota_test.go │ │ ├── clear_backlog.go │ │ ├── clear_backlog_test.go │ │ ├── clear_offload_deletion_lag.go │ │ ├── clusters_test.go │ │ ├── compaction_threshold_test.go │ │ ├── create.go │ │ ├── create_test.go │ │ ├── delete.go │ │ ├── delete_ns_anti_affinity_group.go │ │ ├── delete_test.go │ │ ├── dispatch_rate_test.go │ │ ├── errors_ns.go │ │ ├── get_anti_affinity_ns.go │ │ ├── get_backlog_quota.go │ │ ├── get_compaction_threshold.go │ │ ├── get_dispatch_rate.go │ │ ├── get_is_allow_auto_update_schema.go │ │ ├── get_max_consumers_per_subscription.go │ │ ├── get_max_consumers_per_topic.go │ │ ├── get_max_producers_per_topic.go │ │ ├── get_message_ttl.go │ │ ├── get_ns_anti_affinity_group.go │ │ ├── get_offload_deletion_lag.go │ │ ├── get_offload_threshold.go │ │ ├── get_persistence.go │ │ ├── get_publish_rate.go │ │ ├── get_replication_clusters.go │ │ ├── get_replicator_dispatch_rate.go │ │ ├── get_retention.go │ │ ├── get_schema_autoupdate_strategy.go │ │ ├── get_schema_valudation_enforce.go │ │ ├── get_subscribe_rate.go │ │ ├── get_subscription_dispatch_rate.go │ │ ├── grant_permission.go │ │ ├── grant_permission_test.go │ │ ├── grant_subscription_permission.go │ │ ├── grant_subscription_permission_test.go │ │ ├── is_allow_auto_update_schema_test.go │ │ ├── list.go │ │ ├── max_consumers_per_subscription_test.go │ │ ├── max_consumers_per_topic_test.go │ │ ├── max_producers_per_topic_test.go │ │ ├── message_ttl_test.go │ │ ├── namespace.go │ │ ├── ns_anti_affinity_test.go │ │ ├── offload_deletion_test.go │ │ ├── offload_threshold_test.go │ │ ├── permissions.go │ │ ├── permissions_test.go │ │ ├── persistence_test.go │ │ ├── policies.go │ │ ├── policies_test.go │ │ ├── publish_rate_test.go │ │ ├── remove_backlog_quota.go │ │ ├── remove_topic_auto_creation.go │ │ ├── replicator_dispatch_rate_test.go │ │ ├── retention_test.go │ │ ├── revoke_permission.go │ │ ├── revoke_permission_test.go │ │ ├── revoke_subscription_permission.go │ │ ├── revoke_subscription_permission_test.go │ │ ├── schema_autoupdate_strategy_test.go │ │ ├── schema_validation_enforce_test.go │ │ ├── set_backlog_quota.go │ │ ├── set_compaction_threshold.go │ │ ├── set_deduplication_status.go │ │ ├── set_deduplication_status_test.go │ │ ├── set_dispatch_rate.go │ │ ├── set_encryption_require.go │ │ ├── set_encryption_require_test.go │ │ ├── set_is_allow_auto_update_schema.go │ │ ├── set_max_consumers_per_subscription.go │ │ ├── set_max_consumers_per_topic.go │ │ ├── set_max_producers_per_topic.go │ │ ├── set_message_ttl.go │ │ ├── set_ns_anti_affinity_group.go │ │ ├── set_offload_deletion_lag.go │ │ ├── set_offload_threshold.go │ │ ├── set_persistence.go │ │ ├── set_publish_rate.go │ │ ├── set_replication_clusters.go │ │ ├── set_replicator_dispatch_rate.go │ │ ├── set_retention.go │ │ ├── set_schema_autoupdate_strategy.go │ │ ├── set_schema_validation_enforce.go │ │ ├── set_subscribe_rate.go │ │ ├── set_subscription_auth_mode.go │ │ ├── set_subscription_auth_mode_test.go │ │ ├── set_subscription_dispatch_rate.go │ │ ├── set_topic_auto_creation.go │ │ ├── split_bundle.go │ │ ├── split_bundle_test.go │ │ ├── subscribe_rate_test.go │ │ ├── subscription_dispatch_rate_test.go │ │ ├── test_help.go │ │ ├── topics.go │ │ ├── topics_test.go │ │ ├── unload.go │ │ ├── unsubscribe.go │ │ ├── unsubscribe_test.go │ │ └── upload_test.go │ ├── nsisolationpolicy │ │ ├── broker.go │ │ ├── broker_test.go │ │ ├── brokers.go │ │ ├── delete.go │ │ ├── get.go │ │ ├── list.go │ │ ├── ns_isolation_policy.go │ │ ├── ns_isolation_policy_test.go │ │ ├── set.go │ │ └── test_help.go │ ├── packages │ │ ├── delete.go │ │ ├── delete_test.go │ │ ├── download.go │ │ ├── download_test.go │ │ ├── get_metadata.go │ │ ├── get_metadata_test.go │ │ ├── list.go │ │ ├── list_test.go │ │ ├── list_versions.go │ │ ├── list_versions_test.go │ │ ├── packages.go │ │ ├── test_help.go │ │ ├── update_metadata.go │ │ ├── update_metadata_test.go │ │ ├── upload.go │ │ └── upload_test.go │ ├── plugin │ │ ├── list.go │ │ ├── list_test.go │ │ ├── plugin.go │ │ └── test_help.go │ ├── resourcequotas │ │ ├── get.go │ │ ├── reset.go │ │ ├── resource_quota_test.go │ │ ├── resource_quotas.go │ │ ├── set.go │ │ └── test_help.go │ ├── schemas │ │ ├── delete.go │ │ ├── get.go │ │ ├── schema_test.go │ │ ├── schemas.go │ │ ├── test_help.go │ │ └── upload.go │ ├── sinks │ │ ├── create.go │ │ ├── create_test.go │ │ ├── delete.go │ │ ├── delete_test.go │ │ ├── get.go │ │ ├── get_test.go │ │ ├── list.go │ │ ├── list_built_in_sinks.go │ │ ├── list_test.go │ │ ├── opeations_test.go │ │ ├── restart.go │ │ ├── restart_test.go │ │ ├── sinks.go │ │ ├── start.go │ │ ├── start_test.go │ │ ├── status.go │ │ ├── status_test.go │ │ ├── stop.go │ │ ├── test_help.go │ │ ├── update.go │ │ ├── update_test.go │ │ └── util.go │ ├── sources │ │ ├── create.go │ │ ├── create_test.go │ │ ├── delete.go │ │ ├── delete_test.go │ │ ├── get.go │ │ ├── get_test.go │ │ ├── list.go │ │ ├── list_built_in_sources.go │ │ ├── operations_test.go │ │ ├── restart.go │ │ ├── sources.go │ │ ├── start.go │ │ ├── start_test.go │ │ ├── status.go │ │ ├── status_test.go │ │ ├── stop.go │ │ ├── test_help.go │ │ ├── update.go │ │ ├── update_test.go │ │ └── util.go │ ├── status │ │ ├── check.go │ │ ├── check_test.go │ │ ├── status.go │ │ └── test_help.go │ ├── subscription │ │ ├── args_check.go │ │ ├── create.go │ │ ├── create_test.go │ │ ├── delete.go │ │ ├── delete_test.go │ │ ├── errors_sub.go │ │ ├── expire.go │ │ ├── expire_test.go │ │ ├── get_message_by_id.go │ │ ├── list.go │ │ ├── list_test.go │ │ ├── peek.go │ │ ├── reset_cursor.go │ │ ├── reset_cursor_test.go │ │ ├── skip.go │ │ ├── skip_test.go │ │ ├── subscription.go │ │ └── test_help.go │ ├── tenant │ │ ├── create.go │ │ ├── create_test.go │ │ ├── delete.go │ │ ├── delete_test.go │ │ ├── get.go │ │ ├── get_test.go │ │ ├── list.go │ │ ├── tenant.go │ │ ├── test.go │ │ ├── update.go │ │ └── update_test.go │ ├── token │ │ ├── create.go │ │ ├── create_key_pair.go │ │ ├── create_key_pair_test.go │ │ ├── create_secret_key.go │ │ ├── create_secret_key_test.go │ │ ├── create_test.go │ │ ├── show.go │ │ ├── show_test.go │ │ ├── test_help.go │ │ ├── token.go │ │ ├── validate.go │ │ └── validate_test.go │ ├── topic │ │ ├── args_check.go │ │ ├── backlog_quota_test.go │ │ ├── bundle_range.go │ │ ├── bundle_range_test.go │ │ ├── compact.go │ │ ├── compact_status.go │ │ ├── compact_status_test.go │ │ ├── compact_test.go │ │ ├── compaction_threshold_test.go │ │ ├── create.go │ │ ├── create_test.go │ │ ├── deduplication_status_test.go │ │ ├── delayed_delivery_test.go │ │ ├── delete.go │ │ ├── delete_test.go │ │ ├── dispatch_rate_test.go │ │ ├── errors_topic.go │ │ ├── get.go │ │ ├── get_backlog_quota.go │ │ ├── get_compaction_threshold.go │ │ ├── get_deduplication_status.go │ │ ├── get_delayed_delivery.go │ │ ├── get_dispatch_rate.go │ │ ├── get_inactive_topic.go │ │ ├── get_max_consumers.go │ │ ├── get_max_producers.go │ │ ├── get_max_unack_messages_per_consumer.go │ │ ├── get_max_unack_messages_per_subscription.go │ │ ├── get_message_ttl.go │ │ ├── get_permissions.go │ │ ├── get_permissions_test.go │ │ ├── get_persistence.go │ │ ├── get_publish_rate.go │ │ ├── get_retention.go │ │ ├── get_test.go │ │ ├── grant_permissions.go │ │ ├── grant_permissions_test.go │ │ ├── inactive_topic_test.go │ │ ├── internal.go │ │ ├── internal_test.go │ │ ├── last_messageId.go │ │ ├── last_messageId_test.go │ │ ├── list.go │ │ ├── list_test.go │ │ ├── lookup_topic.go │ │ ├── lookup_topic_test.go │ │ ├── max_consumers_test.go │ │ ├── max_producers_test.go │ │ ├── max_unack_messages_per_consumer_test.go │ │ ├── max_unack_messages_per_subscription_test.go │ │ ├── message_ttl_test.go │ │ ├── offload.go │ │ ├── offload_status.go │ │ ├── offload_status_test.go │ │ ├── offload_test.go │ │ ├── persistence_test.go │ │ ├── publish_rate_test.go │ │ ├── remove_backlog_quota.go │ │ ├── remove_compaction_threshold.go │ │ ├── remove_deduplication_status.go │ │ ├── remove_delayed_delivery.go │ │ ├── remove_dispatch_rate.go │ │ ├── remove_inactive_topic.go │ │ ├── remove_max_consumer.go │ │ ├── remove_max_producers.go │ │ ├── remove_max_unack_messages_per_consumer.go │ │ ├── remove_max_unack_messages_per_subscription.go │ │ ├── remove_message_ttl.go │ │ ├── remove_persistence.go │ │ ├── remove_publish_rate.go │ │ ├── remove_retention.go │ │ ├── retention_test.go │ │ ├── revoke_permissions.go │ │ ├── revoke_permissions_test.go │ │ ├── set_backlog_quota.go │ │ ├── set_compaction_threshold.go │ │ ├── set_deduplication_status.go │ │ ├── set_delayed_delivery.go │ │ ├── set_dispatch_rate.go │ │ ├── set_inactive_topic.go │ │ ├── set_max_consumers.go │ │ ├── set_max_producers.go │ │ ├── set_max_unack_messages_per_consumer.go │ │ ├── set_max_unack_messages_per_subscription.go │ │ ├── set_message_ttl.go │ │ ├── set_persistence.go │ │ ├── set_publish_rate.go │ │ ├── set_retention.go │ │ ├── stats.go │ │ ├── stats_internal.go │ │ ├── stats_internal_test.go │ │ ├── stats_test.go │ │ ├── teminate.go │ │ ├── teminate_test.go │ │ ├── test_help.go │ │ ├── topic.go │ │ ├── unload.go │ │ ├── unload_test.go │ │ ├── update.go │ │ └── update_test.go │ └── utils │ │ └── util.go ├── oauth2 │ ├── active.go │ ├── login.go │ ├── oauth2.go │ └── os │ │ └── os_interactor.go ├── plugin │ └── plugin.go ├── pulsar │ └── common │ │ └── algorithm │ │ ├── algorithm │ │ ├── algorithm.go │ │ └── algorithm_test.go │ │ ├── ecdsa │ │ ├── es256.go │ │ ├── es384.go │ │ └── es512.go │ │ ├── hmac │ │ ├── hs256.go │ │ ├── hs384.go │ │ └── hs512.go │ │ ├── keypair │ │ └── keypair.go │ │ └── rsa │ │ ├── rs256.go │ │ ├── rs384.go │ │ └── rs512.go ├── pulsarctl.go └── test │ ├── base_container.go │ ├── bookkeeper │ ├── bkctl.go │ ├── cluster.go │ ├── cluster_script.go │ ├── cluster_spec.go │ ├── cluster_test.go │ └── containers │ │ ├── bookie.go │ │ └── zookeeper.go │ ├── cluster.go │ ├── pulsar │ ├── cluster.go │ ├── cluster_script.go │ ├── cluster_spec.go │ ├── cluster_test.go │ ├── containers │ │ ├── bookie.go │ │ ├── broker.go │ │ ├── proxy.go │ │ └── zookeeper.go │ ├── standalone.go │ └── standalone_test.go │ ├── token_test.go │ └── utils.go ├── plugins ├── conf │ └── openssl.cnf └── pulsarctl-security_tool ├── scripts ├── build.sh ├── dev │ ├── __init__.py │ └── set-project-version.py ├── entrypoint.sh ├── pulsar-service-shutdown.sh ├── pulsar-service-startup.sh ├── run-integration-tests.sh └── test-docker │ └── Dockerfile ├── site └── gen-pulsarctldocs │ ├── generators │ ├── gen.go │ ├── package-lock.json │ ├── read_cmd.go │ ├── templates.go │ ├── types.go │ └── v1_1 │ │ ├── static_includes │ │ └── _getting_started.md │ │ └── toc.yaml │ └── main.go ├── stable.txt └── test ├── auth ├── certs │ ├── broker-cert.pem │ ├── broker-key.pem │ ├── cacert.pem │ ├── client-cert.pem │ └── client-key.pem ├── tls.env ├── token.env └── token │ └── secret.key ├── client.conf ├── docker └── docker-compose.yml ├── functions ├── example-function-config.yaml └── example-update-function-config.yaml ├── key ├── pulsar-admin-es256-private.key ├── pulsar-admin-es256-public.key ├── pulsar-admin-es384-private.key ├── pulsar-admin-es384-public.key ├── pulsar-admin-es512-private.key ├── pulsar-admin-es512-public.key ├── pulsar-admin-hs256-base64-secret.key ├── pulsar-admin-hs256-secret.key ├── pulsar-admin-hs384-base64-secret.key ├── pulsar-admin-hs384-secret.key ├── pulsar-admin-hs512-base64-secret.key ├── pulsar-admin-hs512-secret.key ├── pulsar-admin-rs256-private.key ├── pulsar-admin-rs256-public.key ├── pulsar-admin-rs384-private.key ├── pulsar-admin-rs384-public.key ├── pulsar-admin-rs512-private.key ├── pulsar-admin-rs512-public.key ├── pulsarctl-es256-private.key ├── pulsarctl-es256-public.key ├── pulsarctl-es384-private.key ├── pulsarctl-es384-public.key ├── pulsarctl-es512-private.key ├── pulsarctl-es512-public.key ├── pulsarctl-hs256-base64-secret.key ├── pulsarctl-hs256-secret.key ├── pulsarctl-hs384-base64-secret.key ├── pulsarctl-hs384-secret.key ├── pulsarctl-hs512-base64-secret.key ├── pulsarctl-hs512-secret.key ├── pulsarctl-rs256-private.key ├── pulsarctl-rs256-public.key ├── pulsarctl-rs384-private.key ├── pulsarctl-rs384-public.key ├── pulsarctl-rs512-private.key └── pulsarctl-rs512-public.key ├── policies └── policies.env ├── script └── check.sh ├── standalone.conf └── token └── standalone.conf /.github/CODEOWNERS: -------------------------------------------------------------------------------- 1 | * @mattisonchao @zymap @nlu90 2 | -------------------------------------------------------------------------------- /.github/release-drafter.yml: -------------------------------------------------------------------------------- 1 | template: | 2 | ## What's changed 3 | $CHANGES 4 | -------------------------------------------------------------------------------- /.github/workflows/ci-auth-checks.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl 2 | on: 3 | pull_request: 4 | branches: 5 | - '*' 6 | path-ignores: 7 | - 'docs/**' 8 | - 'README.md' 9 | - 'CONTRIBUTING.md' 10 | jobs: 11 | auth-tests: 12 | runs-on: ubuntu-latest 13 | steps: 14 | - uses: actions/checkout@v2 15 | - name: Login SN docker hub 16 | run: docker login -u="${{ secrets.DOCKER_USER }}" -p="${{ secrets.DOCKER_PASSWORD}}" 17 | - name: Run token tests 18 | run: scripts/run-integration-tests.sh token 19 | - name: Run TLS tests 20 | run: scripts/run-integration-tests.sh tls 21 | -------------------------------------------------------------------------------- /.github/workflows/ci-bookie-checks.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl 2 | on: 3 | pull_request: 4 | branches: 5 | - '*' 6 | path-ignores: 7 | - 'docs/**' 8 | - 'README.md' 9 | - 'CONTRIBUTING.md' 10 | jobs: 11 | bookie-ut-tests: 12 | runs-on: ubuntu-latest 13 | steps: 14 | - name: Set up Go 1.24 15 | uses: actions/setup-go@v1 16 | with: 17 | go-version: 1.24 18 | id: go 19 | - name: Check out code into the Go module directory 20 | uses: actions/checkout@v2 21 | - name: Run bookKeeper service 22 | run: | 23 | pushd test/docker 24 | docker compose pull 25 | docker compose up -d 26 | popd 27 | - name: Check bookKeeper service 28 | run: | 29 | ./test/script/check.sh bookieHTTP 30 | - name: Write dummy data 31 | run: | 32 | docker exec bk bin/bookkeeper shell simpletest -ensemble 1 -writeQuorum 1 -ackQuorum 1 -numEntries 10 33 | docker exec bk bin/bookkeeper shell simpletest -ensemble 1 -writeQuorum 1 -ackQuorum 1 -numEntries 10 34 | - name: Test 35 | run: | 36 | # docker ps 37 | # CGO_ENABLED=1 go test -v -race ./pkg/bkctl/... 38 | # CGO_ENABLED=1 go test -v -race ./pkg/bookkeeper/... 39 | -------------------------------------------------------------------------------- /.github/workflows/ci-checks.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl 2 | on: 3 | pull_request: 4 | branches: 5 | - '*' 6 | path-ignores: 7 | - 'docs/**' 8 | - 'README.md' 9 | - 'CONTRIBUTING.md' 10 | jobs: 11 | ut-tests: 12 | runs-on: ubuntu-latest 13 | steps: 14 | - name: Login SN docker hub 15 | run: docker login -u="${{ secrets.DOCKER_USER }}" -p="${{ secrets.DOCKER_PASSWORD}}" 16 | - uses: actions/checkout@v2 17 | - name: Run tests 18 | run: scripts/run-integration-tests.sh 19 | -------------------------------------------------------------------------------- /.github/workflows/ci-functions-checks.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl 2 | on: 3 | pull_request: 4 | branches: 5 | - '*' 6 | path-ignores: 7 | - 'docs/**' 8 | - 'README.md' 9 | - 'CONTRIBUTING.md' 10 | jobs: 11 | function-tests: 12 | runs-on: ubuntu-latest 13 | steps: 14 | - name: Login SN docker hub 15 | run: docker login -u="${{ secrets.DOCKER_USER }}" -p="${{ secrets.DOCKER_PASSWORD}}" 16 | - name: Set up Go 1.24 17 | uses: actions/setup-go@v1 18 | with: 19 | go-version: 1.24 20 | id: go 21 | - name: Check out code into the Go module directory 22 | uses: actions/checkout@v2 23 | - name: Function tests 24 | run: scripts/run-integration-tests.sh function 25 | - name: Setup tmate session 26 | if: failure() 27 | uses: mxschmitt/action-tmate@v3 28 | sink-tests: 29 | runs-on: ubuntu-latest 30 | steps: 31 | - name: Login SN docker hub 32 | run: docker login -u="${{ secrets.DOCKER_USER }}" -p="${{ secrets.DOCKER_PASSWORD}}" 33 | - name: Set up Go 1.24 34 | uses: actions/setup-go@v5 35 | with: 36 | go-version: 1.24 37 | id: go 38 | - name: Check out code into the Go module directory 39 | uses: actions/checkout@v2 40 | - name: Sink tests 41 | run: scripts/run-integration-tests.sh sink 42 | source-tests: 43 | runs-on: ubuntu-latest 44 | steps: 45 | - name: Login SN docker hub 46 | run: docker login -u="${{ secrets.DOCKER_USER }}" -p="${{ secrets.DOCKER_PASSWORD}}" 47 | - name: Set up Go 1.24 48 | uses: actions/setup-go@v5 49 | with: 50 | go-version: 1.24 51 | id: go 52 | - name: Check out code into the Go module directory 53 | uses: actions/checkout@v2 54 | - name: Source tests 55 | run: scripts/run-integration-tests.sh source 56 | -------------------------------------------------------------------------------- /.github/workflows/ci-install-script-checks.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl 2 | on: 3 | pull_request: 4 | branches: 5 | - '*' 6 | paths: 7 | - 'install.sh' 8 | - 'stable.txt' 9 | jobs: 10 | install-script-check: 11 | runs-on: ubuntu-latest 12 | steps: 13 | - name: Login SN docker hub 14 | run: docker login -u="${{ secrets.DOCKER_USER }}" -p="${{ secrets.DOCKER_PASSWORD}}" 15 | - name: Check out code into the Go module directory 16 | uses: actions/checkout@v2 17 | - name: Test install 18 | run: | 19 | ./install.sh -u -v v0.3.0 20 | ~/.pulsarctl/pulsarctl help 21 | ./install.sh -u 22 | ~/.pulsarctl/pulsarctl help 23 | -------------------------------------------------------------------------------- /.github/workflows/ci-packages-checks.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl 2 | on: 3 | pull_request: 4 | branches: 5 | - '*' 6 | path-ignores: 7 | - 'docs/**' 8 | - 'README.md' 9 | - 'CONTRIBUTING.md' 10 | jobs: 11 | packages-tests: 12 | runs-on: ubuntu-latest 13 | steps: 14 | - name: Login SN docker hub 15 | run: docker login -u="${{ secrets.DOCKER_USER }}" -p="${{ secrets.DOCKER_PASSWORD}}" 16 | - name: Set up Go 1.24 17 | uses: actions/setup-go@v5 18 | with: 19 | go-version: 1.24 20 | id: go 21 | - name: Check out code into the Go module directory 22 | uses: actions/checkout@v2 23 | - name: Packages tests 24 | run: scripts/run-integration-tests.sh packages 25 | - name: Setup tmate session 26 | if: failure() 27 | uses: mxschmitt/action-tmate@v3 28 | -------------------------------------------------------------------------------- /.github/workflows/ci-release-checks.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl 2 | 3 | on: 4 | pull_request: 5 | branches: 6 | - '*' 7 | path-ignores: 8 | - 'docs/**' 9 | - 'README.md' 10 | - 'CONTRIBUTING.md' 11 | 12 | jobs: 13 | release-check: 14 | runs-on: ubuntu-latest 15 | strategy: 16 | matrix: 17 | go-version: [ 1.24 ] 18 | steps: 19 | - uses: actions/checkout@v2 20 | - uses: actions/setup-go@v5 21 | with: 22 | go-version: ${{ matrix.go-version }} 23 | id: go 24 | 25 | - name: build 26 | run: | 27 | version=`cat VERSION` 28 | CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o pulsarctl-amd64-linux -ldflags "-X github.com/streamnative/pulsarctl/pkg/pulsar.ReleaseVersion=Pulsarctl-Go-$version" . 29 | CGO_ENABLED=0 GOOS=linux GOARCH=386 go build -o pulsarctl-386-linux -ldflags "-X github.com/streamnative/pulsarctl/pkg/pulsar.ReleaseVersion=Pulsarctl-Go-$version" . 30 | CGO_ENABLED=0 GOOS=darwin GOARCH=amd64 go build -o pulsarctl-amd64-darwin -ldflags "-X github.com/streamnative/pulsarctl/pkg/pulsar.ReleaseVersion=Pulsarctl-Go-$version" . 31 | CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build -o pulsarctl-amd64-windows.exe -ldflags "-X github.com/streamnative/pulsarctl/pkg/pulsar.ReleaseVersion=Pulsarctl-Go-$version" . 32 | CGO_ENABLED=0 GOOS=windows GOARCH=386 go build -o pulsarctl-386-windows.exe -ldflags "-X github.com/streamnative/pulsarctl/pkg/pulsar.ReleaseVersion=Pulsarctl-Go-$version" . 33 | - name: build-site 34 | run: | 35 | make cli 36 | -------------------------------------------------------------------------------- /.github/workflows/ci-style-checks.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl 2 | on: 3 | pull_request: 4 | branches: 5 | - '*' 6 | path-ignores: 7 | - 'docs/**' 8 | - 'README.md' 9 | - 'CONTRIBUTING.md' 10 | jobs: 11 | style-check: 12 | runs-on: ubuntu-latest 13 | steps: 14 | - name: Set up Go 1.24 15 | uses: actions/setup-go@v5 16 | with: 17 | go-version: 1.24 18 | id: go 19 | - name: Check out code into the Go module directory 20 | uses: actions/checkout@v2 21 | - name: golangci-lint 22 | uses: golangci/golangci-lint-action@v6 23 | with: 24 | version: v1.64.8 25 | args: --timeout=10m -v 26 | - name: Build 27 | run: go build . 28 | -------------------------------------------------------------------------------- /.github/workflows/ci-trivy.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl 2 | on: 3 | pull_request: 4 | branches: 5 | - '*' 6 | path-ignores: 7 | - 'docs/**' 8 | - 'README.md' 9 | - 'CONTRIBUTING.md' 10 | 11 | jobs: 12 | scan-vulnerabilities: 13 | runs-on: ubuntu-latest 14 | steps: 15 | - name: Set up Go 1.22 16 | uses: actions/setup-go@v1 17 | with: 18 | go-version: 1.22 19 | id: go 20 | 21 | - name: Check out code into the Go module directory 22 | uses: actions/checkout@v2 23 | 24 | - name: Build 25 | run: go build . 26 | 27 | - name: Build docker image 28 | run: docker build -f docker/amd64-linux.Dockerfile -t pulsarctl . 29 | 30 | - name: Run Trivy vulnerability scanner 31 | uses: aquasecurity/trivy-action@master 32 | with: 33 | image-ref: 'pulsarctl:latest' 34 | format: 'table' 35 | exit-code: '1' 36 | severity: "MEDIUM,HIGH,CRITICAL" 37 | vuln-type: "library" -------------------------------------------------------------------------------- /.github/workflows/documentbot.yml: -------------------------------------------------------------------------------- 1 | 2 | # 3 | # Licensed to the Apache Software Foundation (ASF) under one 4 | # or more contributor license agreements. See the NOTICE file 5 | # distributed with this work for additional information 6 | # regarding copyright ownership. The ASF licenses this file 7 | # to you under the Apache License, Version 2.0 (the 8 | # "License"); you may not use this file except in compliance 9 | # with the License. You may obtain a copy of the License at 10 | # 11 | # http://www.apache.org/licenses/LICENSE-2.0 12 | # 13 | # Unless required by applicable law or agreed to in writing, 14 | # software distributed under the License is distributed on an 15 | # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 | # KIND, either express or implied. See the License for the 17 | # specific language governing permissions and limitations 18 | # under the License. 19 | # 20 | 21 | name: Auto Labeling 22 | 23 | on: 24 | pull_request_target : 25 | types: 26 | - opened 27 | - edited 28 | - labeled 29 | 30 | 31 | 32 | # A GitHub token created for a PR coming from a fork doesn't have 33 | # 'admin' or 'write' permission (which is required to add labels) 34 | # To avoid this issue, you can use the `scheduled` event and run 35 | # this action on a certain interval.And check the label about the 36 | # document. 37 | 38 | jobs: 39 | labeling: 40 | if: ${{ github.repository == 'streamnative/pulsarctl' }} 41 | permissions: 42 | pull-requests: write 43 | runs-on: ubuntu-latest 44 | steps: 45 | - uses: actions/checkout@v2 46 | 47 | - uses: streamnative/github-workflow-libraries/doc-label-check@master 48 | with: 49 | github-token: ${{ secrets.GITHUB_TOKEN }} 50 | label-pattern: '- \[(.*?)\] ?`(.+?)`' # matches '- [x] `label`' 51 | 52 | -------------------------------------------------------------------------------- /.github/workflows/release-note.yml: -------------------------------------------------------------------------------- 1 | name: Pulsarctl Release Note 2 | 3 | on: 4 | push: 5 | branches: 6 | - master 7 | path-ignores: 8 | - 'docs/**' 9 | - 'README.md' 10 | - 'CONTRIBUTING.md' 11 | jobs: 12 | build: 13 | 14 | runs-on: ubuntu-latest 15 | 16 | steps: 17 | - name: release note 18 | uses: release-drafter/release-drafter@v5 19 | env: 20 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} 21 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Binaries for programs and plugins 2 | *.exe 3 | *.exe~ 4 | *.dll 5 | *.so 6 | *.dylib 7 | pulsarctl 8 | bin/ 9 | test/functions/api-examples.jar 10 | dummyExample.jar 11 | pulsar-io-kafka-2.4.0.nar 12 | kafka-clients-0.10.2.1.jar 13 | pulsar-io-jdbc-2.4.0.nar 14 | data 15 | 16 | # Website 17 | 18 | site/gen-pulsarctldocs/generators/includes 19 | site/gen-pulsarctldocs/generators/build/* 20 | 21 | # Test binary, build with `go test -c` 22 | *.test 23 | 24 | # Output of the go coverage tool, specifically when used with LiteIDE 25 | *.out 26 | 27 | # Intellij 28 | .idea 29 | 30 | # Mac 31 | .DS_Store 32 | 33 | # Binary distribution 34 | pulsarctl*.tar.gz 35 | pulsarctl-site-*.tar.gz 36 | release 37 | dist 38 | 39 | # Vscode 40 | .vscode 41 | -------------------------------------------------------------------------------- /.header: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | MINOR_VERSION=1 2 | VERSION=$(shell cat VERSION) 3 | 4 | LDFLAGS += -X "github.com/streamnative/pulsarctl/pkg/cmdutils.ReleaseVersion=$(shell git describe --tags --always)" 5 | LDFLAGS += -X "github.com/streamnative/pulsarctl/pkg/cmdutils.BuildTS=$(shell date -u '+%Y-%m-%d %H:%M:%S')" 6 | LDFLAGS += -X "github.com/streamnative/pulsarctl/pkg/cmdutils.GitHash=$(shell git rev-parse HEAD)" 7 | LDFLAGS += -X "github.com/streamnative/pulsarctl/pkg/cmdutils.GitBranch=$(shell git rev-parse --abbrev-ref HEAD)" 8 | LDFLAGS += -X "github.com/streamnative/pulsarctl/pkg/cmdutils.GoVersion=$(shell go version)" 9 | 10 | GO := GO111MODULE=on go 11 | GOBUILD := $(GO) build 12 | 13 | # Build pulsarctl binary & docs 14 | 15 | cleancli: 16 | rm -f main 17 | rm -rf $(shell pwd)/site/gen-pulsarctldocs/generators/pulsarctl-site-${VERSION}.tar.gz 18 | rm -rf $(shell pwd)/site/gen-pulsarctldocs/generators/includes 19 | rm -rf $(shell pwd)/site/gen-pulsarctldocs/generators/build 20 | rm -rf $(shell pwd)/site/gen-pulsarctldocs/generators/manifest.json 21 | 22 | cli: cleancli 23 | export GO111MODULE=on 24 | go run site/gen-pulsarctldocs/main.go --pulsar-version v1_$(MINOR_VERSION) 25 | docker run -v ${PWD}/site/gen-pulsarctldocs/generators/includes:/source -v ${PWD}/site/gen-pulsarctldocs/generators/build:/build -v ${PWD}/site/gen-pulsarctldocs/generators/:/manifest pwittrock/brodocs 26 | tar -czvf ${PWD}/site/gen-pulsarctldocs/generators/pulsarctl-site-${VERSION}.tar.gz -C ${PWD}/site/gen-pulsarctldocs/generators/build/ . 27 | mv ${PWD}/site/gen-pulsarctldocs/generators/pulsarctl-site-${VERSION}.tar.gz ${PWD}/pulsarctl-site-${VERSION}.tar.gz 28 | 29 | pulsarctl: 30 | $(GOBUILD) -ldflags '$(LDFLAGS)' -o bin/pulsarctl 31 | 32 | .PHONY: install 33 | install: 34 | go install github.com/streamnative/pulsarctl 35 | -------------------------------------------------------------------------------- /VERSION: -------------------------------------------------------------------------------- 1 | 0.6.0-SNAPSHOT 2 | -------------------------------------------------------------------------------- /docker/amd64-linux.Dockerfile: -------------------------------------------------------------------------------- 1 | FROM alpine:3.20 2 | 3 | ADD pulsarctl /usr/local/bin/pulsarctl 4 | 5 | RUN apk add tzdata ca-certificates --no-cache \ 6 | && chmod +x /usr/local/bin/pulsarctl 7 | -------------------------------------------------------------------------------- /golangci.yml: -------------------------------------------------------------------------------- 1 | run: 2 | deadline: 6m 3 | 4 | linters: 5 | disable-all: true 6 | enable: 7 | - bodyclose 8 | - deadcode 9 | - gocritic 10 | - goimports 11 | - golint 12 | - gosimple 13 | - govet 14 | - ineffassign 15 | - interfacer 16 | - misspell 17 | - staticcheck 18 | - structcheck 19 | - stylecheck 20 | - typecheck 21 | - unconvert 22 | - unparam 23 | - unused 24 | - varcheck 25 | - lll 26 | - prealloc 27 | -------------------------------------------------------------------------------- /main.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package main 19 | 20 | import ( 21 | "fmt" 22 | "os" 23 | 24 | "github.com/streamnative/pulsarctl/pkg" 25 | "github.com/streamnative/pulsarctl/pkg/plugin" 26 | ) 27 | 28 | func main() { 29 | rootCmd := pkg.NewPulsarctlCmd() 30 | handler := plugin.NewDefaultPluginHandler(plugin.ValidPluginFilenamePrefixes) 31 | 32 | _, _, err := rootCmd.Find(os.Args) 33 | if err != nil { 34 | err = plugin.HandlePluginCommand(handler, getArgs()) 35 | if err != nil { 36 | fmt.Println(err) 37 | os.Exit(-1) 38 | } 39 | } 40 | 41 | if err = rootCmd.Execute(); err != nil { 42 | fmt.Println(err) // outputs cobra errors 43 | os.Exit(-1) 44 | } 45 | } 46 | 47 | func getArgs() []string { 48 | args := os.Args 49 | if len(args) > 1 { 50 | return args[1:] 51 | } 52 | return []string{} 53 | } 54 | -------------------------------------------------------------------------------- /pkg/bkctl/autorecovery/autorecovery.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package autorecovery 19 | 20 | import ( 21 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 22 | 23 | "github.com/spf13/cobra" 24 | ) 25 | 26 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 27 | resourceCmd := cmdutils.NewResourceCmd( 28 | "auto-recovery", 29 | "Operations about auto recovering", 30 | "", 31 | "") 32 | 33 | commands := []func(*cmdutils.VerbCmd){ 34 | recoverBookieCmd, 35 | listUnderReplicatedLedgerCmd, 36 | whoIsAuditorCmd, 37 | triggerAuditCmd, 38 | setLostBookieRecoveryDelayCmd, 39 | getLostBookieRecoveryDelayCmd, 40 | decommissionCmd, 41 | } 42 | 43 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, commands...) 44 | 45 | return resourceCmd 46 | } 47 | -------------------------------------------------------------------------------- /pkg/bkctl/autorecovery/decommission_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package autorecovery 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestDecommissionArgsErr(t *testing.T) { 27 | // no args specified 28 | args := []string{"decommission"} 29 | _, _, nameErr, err := testAutoRecoveryCommands(decommissionCmd, args) 30 | if err != nil { 31 | t.Fatal(err) 32 | } 33 | 34 | assert.NotNil(t, nameErr) 35 | assert.Equal(t, "the bookie address is not specified or the bookie address is specified more than one", 36 | nameErr.Error()) 37 | 38 | // more than one args specified 39 | args = []string{"decommission", "bookie-1:3181", "bookie-2:3181"} 40 | _, _, nameErr, err = testAutoRecoveryCommands(decommissionCmd, args) 41 | if err != nil { 42 | t.Fatal(err) 43 | } 44 | 45 | assert.NotNil(t, nameErr) 46 | assert.Equal(t, "the bookie address is not specified or the bookie address is specified more than one", 47 | nameErr.Error()) 48 | } 49 | -------------------------------------------------------------------------------- /pkg/bkctl/autorecovery/recover_bookie_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package autorecovery 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestRecoverBookieArgsErr(t *testing.T) { 27 | args := []string{"recover-bookie"} 28 | _, _, nameErr, err := testAutoRecoveryCommands(recoverBookieCmd, args) 29 | if err != nil { 30 | t.Fatal(err) 31 | } 32 | 33 | assert.NotNil(t, nameErr) 34 | assert.Equal(t, "you need to specify the recover bookies id", nameErr.Error()) 35 | } 36 | -------------------------------------------------------------------------------- /pkg/bkctl/bk.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bkctl 19 | 20 | import ( 21 | "github.com/streamnative/pulsarctl/pkg/bkctl/autorecovery" 22 | "github.com/streamnative/pulsarctl/pkg/bkctl/bookie" 23 | "github.com/streamnative/pulsarctl/pkg/bkctl/ledger" 24 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 25 | 26 | "github.com/spf13/cobra" 27 | ) 28 | 29 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 30 | resourceCmd := cmdutils.NewResourceCmd( 31 | "bookkeeper", 32 | "Operations about bookKeeper", 33 | "", 34 | "bk", 35 | ) 36 | 37 | resourceCmd.AddCommand(bookie.Command(flagGrouping)) 38 | resourceCmd.AddCommand(ledger.Command(flagGrouping)) 39 | resourceCmd.AddCommand(autorecovery.Command(flagGrouping)) 40 | 41 | return resourceCmd 42 | } 43 | -------------------------------------------------------------------------------- /pkg/bkctl/bookie/bookie.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookie 19 | 20 | import ( 21 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 22 | 23 | "github.com/spf13/cobra" 24 | ) 25 | 26 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 27 | resourceCmd := cmdutils.NewResourceCmd( 28 | "bookie", 29 | "Operations about one bookie", 30 | "") 31 | 32 | commands := []func(*cmdutils.VerbCmd){ 33 | lastLogMarkCmd, 34 | listDiskFileCmd, 35 | expandStorageCmd, 36 | gcCmd, 37 | gcStatusCmd, 38 | gcDetailsCmd, 39 | stateCmd, 40 | setReadonlyStateCmd, 41 | } 42 | 43 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, commands...) 44 | return resourceCmd 45 | } 46 | -------------------------------------------------------------------------------- /pkg/bkctl/bookie/expand_storage_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookie 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestExpandStorageCmd(t *testing.T) { 27 | args := []string{"expand-storage"} 28 | out, execErr, nameErr, err := testBookieCommands(expandStorageCmd, args) 29 | assert.Nil(t, err) 30 | assert.Nil(t, nameErr) 31 | assert.Nil(t, execErr) 32 | assert.Equal(t, "Successfully expand the storage.\n", out.String()) 33 | } 34 | -------------------------------------------------------------------------------- /pkg/bkctl/bookie/gc_details_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookie 19 | 20 | import ( 21 | "encoding/json" 22 | "testing" 23 | 24 | "github.com/streamnative/pulsarctl/pkg/bookkeeper/bkdata" 25 | "github.com/stretchr/testify/assert" 26 | ) 27 | 28 | func TestGCDetailsCmd(t *testing.T) { 29 | args := []string{"gc-details"} 30 | out, execErr, nameErr, err := testBookieCommands(gcDetailsCmd, args) 31 | assert.Nil(t, err) 32 | assert.Nil(t, nameErr) 33 | assert.Nil(t, execErr) 34 | 35 | var result []bkdata.GCStatus 36 | assert.NoError(t, json.Unmarshal(out.Bytes(), &result)) 37 | assert.Equal(t, 1, len(result)) 38 | assert.False(t, result[0].ForceCompacting) 39 | assert.False(t, result[0].MajorCompacting) 40 | assert.False(t, result[0].MinorCompacting) 41 | assert.NotEqual(t, 0, result[0].LastMajorCompactionTime) 42 | assert.NotEqual(t, 0, result[0].LastMinorCompactionTime) 43 | assert.Equal(t, int64(0), result[0].MajorCompactionCounter) 44 | assert.Equal(t, int64(0), result[0].MinorCompactionCounter) 45 | } 46 | -------------------------------------------------------------------------------- /pkg/bkctl/bookie/gc_status_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookie 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestGCStatusCmd(t *testing.T) { 27 | args := []string{"gc-status"} 28 | out, execErr, nameErr, err := testBookieCommands(gcStatusCmd, args) 29 | assert.Nil(t, err) 30 | assert.Nil(t, nameErr) 31 | assert.Nil(t, execErr) 32 | assert.Equal(t, 33 | "{\n"+ 34 | " \"is_in_force_gc\": \"false\"\n"+ 35 | "}\n"+ 36 | "", 37 | out.String()) 38 | } 39 | -------------------------------------------------------------------------------- /pkg/bkctl/bookie/gc_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookie 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestGCCmd(t *testing.T) { 27 | args := []string{"gc"} 28 | out, execErr, nameErr, err := testBookieCommands(gcCmd, args) 29 | assert.Nil(t, err) 30 | assert.Nil(t, nameErr) 31 | assert.Nil(t, execErr) 32 | assert.Equal(t, "Successfully trigger garbage collection.\n", out.String()) 33 | } 34 | -------------------------------------------------------------------------------- /pkg/bkctl/bookie/last_log_mark_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookie 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestLastLogMarkCmd(t *testing.T) { 27 | args := []string{"last-log-marker"} 28 | out, execErr, nameErr, err := testBookieCommands(lastLogMarkCmd, args) 29 | assert.Nil(t, err) 30 | assert.Nil(t, nameErr) 31 | assert.Nil(t, execErr) 32 | assert.Equal(t, "{\n \"LastLogMark: Journal Id - 0(0.txn)\": \"Pos - 0\"\n}\n", out.String()) 33 | } 34 | -------------------------------------------------------------------------------- /pkg/bkctl/bookie/list_disk_file_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookie 19 | 20 | import ( 21 | "fmt" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestListDiskFileArgError(t *testing.T) { 28 | args := []string{"list-disk-file"} 29 | _, _, nameErr, _ := testBookieCommands(listDiskFileCmd, args) 30 | assert.NotNil(t, nameErr) 31 | assert.Equal(t, "the file type is not specified or the file type is specified more than one", 32 | nameErr.Error()) 33 | 34 | args = []string{"list-disk-file", "invalid"} 35 | _, execErr, _, _ := testBookieCommands(listDiskFileCmd, args) 36 | assert.NotNil(t, execErr) 37 | assert.Equal(t, fmt.Sprintf("invalid file type %s, the file type only can be specified as 'journal', "+ 38 | "'entrylog', 'index'", "invalid"), execErr.Error()) 39 | } 40 | -------------------------------------------------------------------------------- /pkg/bkctl/bookie/set_readonly_state_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookie 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestSetReadonlyStateCmd(t *testing.T) { 27 | args := []string{"set-readonly", "true"} 28 | out, execErr, nameErr, err := testBookieCommands(setReadonlyStateCmd, args) 29 | assert.Nil(t, err) 30 | assert.Nil(t, nameErr) 31 | assert.Nil(t, execErr) 32 | assert.Equal(t, "\"Successfully set the readonly state of a bookie\"\n", out.String()) 33 | 34 | // set back to false, otherwise the next test will fail 35 | args = []string{"set-readonly", "false"} 36 | out, execErr, nameErr, err = testBookieCommands(setReadonlyStateCmd, args) 37 | assert.Nil(t, err) 38 | assert.Nil(t, nameErr) 39 | assert.Nil(t, execErr) 40 | assert.Equal(t, "\"Successfully set the readonly state of a bookie\"\n", out.String()) 41 | } 42 | -------------------------------------------------------------------------------- /pkg/bkctl/bookie/state_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookie 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestStateCmd(t *testing.T) { 27 | args := []string{"state"} 28 | out, execErr, nameErr, err := testBookieCommands(stateCmd, args) 29 | assert.Nil(t, err) 30 | assert.Nil(t, nameErr) 31 | assert.Nil(t, execErr) 32 | assert.Equal(t, 33 | "{\n"+ 34 | " \"running\": true,\n"+ 35 | " \"readOnly\": false,\n"+ 36 | " \"shuttingDown\": false,\n"+ 37 | " \"availableForHighPriorityWrites\": true\n"+ 38 | "}\n"+ 39 | "", 40 | out.String()) 41 | } 42 | -------------------------------------------------------------------------------- /pkg/bkctl/bookies/bookies.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookies 19 | 20 | import ( 21 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 22 | 23 | "github.com/spf13/cobra" 24 | ) 25 | 26 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 27 | resourceCmd := cmdutils.NewResourceCmd( 28 | "bookies", 29 | "Operations about BookKeeper cluster", 30 | "") 31 | 32 | commands := []func(*cmdutils.VerbCmd){ 33 | listCmd, 34 | diskUsageInfoCmd, 35 | } 36 | 37 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, commands...) 38 | return resourceCmd 39 | } 40 | -------------------------------------------------------------------------------- /pkg/bkctl/bookies/disk_usage_info_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookies 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestDiskUsageInfoCmd(t *testing.T) { 28 | args := []string{"disk-usage-info"} 29 | out, execErr, nameErr, err := testBookiesCommands(args) 30 | assert.Nil(t, err) 31 | assert.Nil(t, nameErr) 32 | assert.Nil(t, execErr) 33 | assert.True(t, strings.Contains(out.String(), "3181")) 34 | } 35 | -------------------------------------------------------------------------------- /pkg/bkctl/bookies/test_help.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookies 19 | 20 | import ( 21 | "bytes" 22 | 23 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 24 | 25 | "github.com/kris-nova/logger" 26 | "github.com/spf13/cobra" 27 | ) 28 | 29 | func testBookiesCommands(args []string) (out *bytes.Buffer, 30 | execErr, nameErr, err error) { 31 | 32 | var execError error 33 | cmdutils.ExecErrorHandler = func(err error) { 34 | execError = err 35 | } 36 | 37 | var nameError error 38 | cmdutils.CheckNameArgError = func(err error) { 39 | nameError = err 40 | } 41 | 42 | var rootCmd = &cobra.Command{ 43 | Use: "pulsarctl [command]", 44 | Short: "a CLI for Apache Pulsar", 45 | Run: func(cmd *cobra.Command, _ []string) { 46 | if err := cmd.Help(); err != nil { 47 | logger.Debug("ignoring error %q", err.Error()) 48 | } 49 | }, 50 | } 51 | 52 | buf := new(bytes.Buffer) 53 | rootCmd.SetOut(buf) 54 | rootCmd.SetArgs(append([]string{"bookies"}, args...)) 55 | flagGrouping := cmdutils.NewGrouping() 56 | rootCmd.AddCommand(Command(flagGrouping)) 57 | err = rootCmd.Execute() 58 | 59 | return buf, execError, nameError, err 60 | } 61 | -------------------------------------------------------------------------------- /pkg/bkctl/ledger/errors.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package ledger 19 | 20 | import "github.com/streamnative/pulsarctl/pkg/cmdutils" 21 | 22 | var argError = cmdutils.Output{ 23 | Desc: "the ledger id is not specified or the ledger id is specified more than one", 24 | Out: "[✖] the ledger id is not specified or the ledger id is specified more than one", 25 | } 26 | -------------------------------------------------------------------------------- /pkg/bkctl/ledger/ledger.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package ledger 19 | 20 | import ( 21 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 22 | 23 | "github.com/spf13/cobra" 24 | ) 25 | 26 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 27 | resourceCmd := cmdutils.NewResourceCmd( 28 | "ledger", 29 | "Operations about ledger", 30 | "", 31 | "") 32 | 33 | commands := []func(*cmdutils.VerbCmd){ 34 | deleteCmd, 35 | getCmd, 36 | listCmd, 37 | readCmd, 38 | } 39 | 40 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, commands...) 41 | 42 | return resourceCmd 43 | } 44 | -------------------------------------------------------------------------------- /pkg/bkctl/ledger/list_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package ledger 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestListCmd(t *testing.T) { 28 | o := doListCmdTest(t) 29 | assert.True(t, strings.Contains(o, "0")) 30 | } 31 | 32 | func doListCmdTest(t *testing.T) string { 33 | args := []string{"list"} 34 | out, execErr, nameErr, err := testLedgerCommands(listCmd, args) 35 | assert.Nil(t, err) 36 | assert.Nil(t, nameErr) 37 | assert.Nil(t, execErr) 38 | return out.String() 39 | } 40 | -------------------------------------------------------------------------------- /pkg/bookkeeper/admin_config.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookkeeper 19 | 20 | import ( 21 | "time" 22 | 23 | "github.com/streamnative/pulsarctl/pkg/bookkeeper/bkdata" 24 | ) 25 | 26 | const ( 27 | DefaultWebServiceURL = "http://localhost:8080" 28 | DefaultHTTPTimeOutDuration = 5 * time.Minute 29 | ) 30 | 31 | var ReleaseVersion = "None" 32 | 33 | // Config is used to configure the bookKeeper admin client 34 | type Config struct { 35 | WebServiceURL string 36 | HTTPTimeout time.Duration 37 | APIVersion bkdata.APIVersion 38 | } 39 | 40 | // DefaultConfig for a bookKeeper admin client 41 | func DefaultConfig() *Config { 42 | return &Config{ 43 | WebServiceURL: DefaultWebServiceURL, 44 | HTTPTimeout: DefaultHTTPTimeOutDuration, 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /pkg/bookkeeper/bkdata/api_version.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bkdata 19 | 20 | type APIVersion int 21 | 22 | const ( 23 | V1 APIVersion = iota 24 | ) 25 | 26 | const DefaultAPIVersion = "v1" 27 | 28 | func (v APIVersion) String() string { 29 | if v == V1 { 30 | return "v1" 31 | } 32 | 33 | return DefaultAPIVersion 34 | } 35 | -------------------------------------------------------------------------------- /pkg/bookkeeper/bkdata/autorecovery_data.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bkdata 19 | 20 | type RecoveryRequest struct { 21 | BookieSrc []string `json:"bookie_src"` 22 | DeleteCookie bool `json:"delete_cookie"` 23 | } 24 | 25 | type LostBookieRecoverDelayRequest struct { 26 | DelaySeconds int `json:"delay_seconds"` 27 | } 28 | 29 | type DecommissionRequest struct { 30 | BookieSrc string `json:"bookie_src"` 31 | } 32 | -------------------------------------------------------------------------------- /pkg/bookkeeper/bkdata/bookie_data.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bkdata 19 | 20 | type GCStatus struct { 21 | // whether the GC thread is in force GC 22 | ForceCompacting bool `json:"forceCompacting"` 23 | // whether the GC thread is in major compacting 24 | MajorCompacting bool `json:"majorCompacting"` 25 | // whether the GC thread is in minor compacting 26 | MinorCompacting bool `json:"minorCompacting"` 27 | 28 | LastMajorCompactionTime int64 `json:"lastMajorCompactionTime"` 29 | LastMinorCompactionTime int64 `json:"lastMinorCompactionTime"` 30 | MajorCompactionCounter int64 `json:"majorCompactionCounter"` 31 | MinorCompactionCounter int64 `json:"minorCompactionCounter"` 32 | } 33 | 34 | type ReadonlyState struct { 35 | ReadOnly bool `json:"readOnly"` 36 | } 37 | 38 | type State struct { 39 | Running bool `json:"running"` 40 | ReadOnly bool `json:"readOnly"` 41 | ShuttingDown bool `json:"shuttingDown"` 42 | AvailableForHighPriorityWrites bool `json:"availableForHighPriorityWrites"` 43 | } 44 | -------------------------------------------------------------------------------- /pkg/bookkeeper/bkdata/bookie_type.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bkdata 19 | 20 | import ( 21 | "strings" 22 | 23 | "github.com/pkg/errors" 24 | ) 25 | 26 | type BookieType string 27 | 28 | const ( 29 | rw BookieType = "rw" 30 | ro BookieType = "ro" 31 | ) 32 | 33 | func ParseBookieType(t string) (BookieType, error) { 34 | switch strings.ToLower(t) { 35 | case rw.String(): 36 | return rw, nil 37 | case ro.String(): 38 | return ro, nil 39 | default: 40 | return "", errors.Errorf("invalid bookie type %s, the bookie type only can "+ 41 | "be specified as 'rw' or 'ro'", t) 42 | } 43 | } 44 | 45 | func (t BookieType) String() string { 46 | return string(t) 47 | } 48 | -------------------------------------------------------------------------------- /pkg/bookkeeper/bkdata/bookie_type_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bkdata 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/pkg/errors" 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | var testParseBookieTypeData = []struct { 28 | bookieType string 29 | parsedBookieType BookieType 30 | errString string 31 | }{ 32 | {"rw", rw, ""}, 33 | {"ro", ro, ""}, 34 | {"", "", bookieTypeErrStr("")}, 35 | {"r", "", bookieTypeErrStr("r")}, 36 | } 37 | 38 | func TestParseBookieType(t *testing.T) { 39 | for _, data := range testParseBookieTypeData { 40 | bkt, err := ParseBookieType(data.bookieType) 41 | if data.errString != "" { 42 | assert.NotNil(t, err) 43 | assert.Equal(t, data.errString, err.Error()) 44 | continue 45 | } 46 | assert.Equal(t, data.parsedBookieType, bkt) 47 | } 48 | } 49 | 50 | func bookieTypeErrStr(bookieType string) string { 51 | return errors.Errorf( 52 | "invalid bookie type %s, the bookie type only can be specified as 'rw' or 'ro'", bookieType).Error() 53 | } 54 | -------------------------------------------------------------------------------- /pkg/bookkeeper/bkdata/file_type.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bkdata 19 | 20 | import ( 21 | "strings" 22 | 23 | "github.com/pkg/errors" 24 | ) 25 | 26 | type FileType string 27 | 28 | const ( 29 | journal FileType = "journal" 30 | entryLog FileType = "entrylog" 31 | index FileType = "index" 32 | ) 33 | 34 | func ParseFileType(fileType string) (FileType, error) { 35 | switch strings.ToLower(fileType) { 36 | case journal.String(): 37 | return journal, nil 38 | case entryLog.String(): 39 | return entryLog, nil 40 | case index.String(): 41 | return index, nil 42 | default: 43 | return "", errors.Errorf("invalid file type %s, the file type only can be specified as 'journal', "+ 44 | "'entrylog', 'index'", fileType) 45 | } 46 | } 47 | 48 | func (t FileType) String() string { 49 | return string(t) 50 | } 51 | -------------------------------------------------------------------------------- /pkg/bookkeeper/bkdata/file_type_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bkdata 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/pkg/errors" 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | var testParseFileTypeData = []struct { 28 | fileType string 29 | parsedFileType FileType 30 | errString string 31 | }{ 32 | {"journal", journal, ""}, 33 | {"entrylog", entryLog, ""}, 34 | {"index", index, ""}, 35 | {"", "", fileTypeErrStr("")}, 36 | {"invalid", "", fileTypeErrStr("invalid")}, 37 | } 38 | 39 | func TestParseFileType(t *testing.T) { 40 | for _, data := range testParseFileTypeData { 41 | ft, err := ParseFileType(data.fileType) 42 | if data.errString != "" { 43 | assert.NotNil(t, err) 44 | assert.Equal(t, data.errString, err.Error()) 45 | continue 46 | } 47 | assert.Equal(t, data.parsedFileType, ft) 48 | } 49 | } 50 | 51 | func fileTypeErrStr(fileType string) string { 52 | return errors.Errorf( 53 | "invalid file type %s, the file type only can be specified as 'journal', "+ 54 | "'entrylog', 'index'", fileType).Error() 55 | } 56 | -------------------------------------------------------------------------------- /pkg/cmdutils/version.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package cmdutils 19 | 20 | import "fmt" 21 | 22 | // Version information. 23 | var ( 24 | ReleaseVersion = "None" 25 | BuildTS = "None" 26 | GitHash = "None" 27 | GitBranch = "None" 28 | GoVersion = "None" 29 | ) 30 | 31 | // Print out the version information. 32 | func PrintVersionInfo() { 33 | fmt.Printf("Release Version: %s\n", ReleaseVersion) 34 | fmt.Printf("Git Commit Hash: %s\n", GitHash) 35 | fmt.Printf("Git Branch: %s\n", GitBranch) 36 | fmt.Printf("UTC Build Time: %s\n", BuildTS) 37 | fmt.Printf("Go Version: %s\n", GoVersion) 38 | } 39 | -------------------------------------------------------------------------------- /pkg/ctl/brokers/broker.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokers 19 | 20 | import ( 21 | "github.com/spf13/cobra" 22 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 23 | ) 24 | 25 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 26 | resourceCmd := cmdutils.NewResourceCmd( 27 | "brokers", 28 | "Operations about broker(s)", 29 | "", 30 | "broker") 31 | 32 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getBrokerListCmd) 33 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getDynamicConfigListNameCmd) 34 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getOwnedNamespacesCmd) 35 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, updateDynamicConfig) 36 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, deleteDynamicConfigCmd) 37 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getAllDynamicConfigsCmd) 38 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getInternalConfigCmd) 39 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getRuntimeConfigCmd) 40 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, healthCheckCmd) 41 | 42 | return resourceCmd 43 | } 44 | -------------------------------------------------------------------------------- /pkg/ctl/brokers/config_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokers 19 | 20 | import ( 21 | "encoding/json" 22 | "testing" 23 | 24 | "github.com/apache/pulsar-client-go/pulsaradmin/pkg/utils" 25 | "github.com/stretchr/testify/assert" 26 | ) 27 | 28 | func TestGetInternalConfig(t *testing.T) { 29 | args := []string{"get-internal-config"} 30 | internalOut, execErr, _, _ := TestBrokersCommands(getInternalConfigCmd, args) 31 | assert.Nil(t, execErr) 32 | 33 | var internalData utils.InternalConfigurationData 34 | err := json.Unmarshal(internalOut.Bytes(), &internalData) 35 | assert.Nil(t, err) 36 | } 37 | 38 | func TestGetRuntimeConfig(t *testing.T) { 39 | args := []string{"get-runtime-config"} 40 | runtimeOut, execErr, _, _ := TestBrokersCommands(getRuntimeConfigCmd, args) 41 | assert.Nil(t, execErr) 42 | 43 | var runtimeConf map[string]string 44 | err := json.Unmarshal(runtimeOut.Bytes(), &runtimeConf) 45 | assert.Nil(t, err) 46 | assert.True(t, len(runtimeConf) != 0) 47 | } 48 | -------------------------------------------------------------------------------- /pkg/ctl/brokers/delete_dynamic_config_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokers 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestDeleteDynamicConfig(t *testing.T) { 28 | args := []string{"delete-dynamic-config", "--config", "dispatcherMinReadBatchSize"} 29 | delOut, execErr, _, _ := TestBrokersCommands(deleteDynamicConfigCmd, args) 30 | assert.Nil(t, execErr) 31 | expectedOut := "Deleted dynamic config: dispatcherMinReadBatchSize successful\n" 32 | assert.Equal(t, expectedOut, delOut.String()) 33 | 34 | failArgs := []string{"delete-dynamic-config", "--config", "errorName"} 35 | _, nameErr, _, _ := TestBrokersCommands(deleteDynamicConfigCmd, failArgs) 36 | assert.NotNil(t, nameErr) 37 | assert.True(t, strings.Contains(nameErr.Error(), "code: 412")) 38 | } 39 | -------------------------------------------------------------------------------- /pkg/ctl/brokers/healthcheck_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokers 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestHealthCheck(t *testing.T) { 28 | args := []string{"healthcheck"} 29 | checkOut, execErr, _, _ := TestBrokersCommands(healthCheckCmd, args) 30 | assert.Nil(t, execErr) 31 | str := strings.ReplaceAll(checkOut.String(), "\n", "") 32 | assert.Equal(t, "ok", str) 33 | } 34 | -------------------------------------------------------------------------------- /pkg/ctl/brokers/list_dynamic_config_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokers 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestGetDynamicConfigListNameCmd(t *testing.T) { 27 | args := []string{"list-dynamic-config"} 28 | listOut, execErr, _, _ := TestBrokersCommands(getDynamicConfigListNameCmd, args) 29 | assert.Nil(t, execErr) 30 | expectedOut := "" 31 | assert.NotEqual(t, expectedOut, listOut.String()) 32 | } 33 | -------------------------------------------------------------------------------- /pkg/ctl/brokers/list_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokers 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestListBrokers(t *testing.T) { 28 | args := []string{"list", "standalone"} 29 | listOut, execErr, _, _ := TestBrokersCommands(getBrokerListCmd, args) 30 | assert.Nil(t, execErr) 31 | assert.True(t, strings.Contains(listOut.String(), "8080")) 32 | 33 | failArgs := []string{"list"} 34 | _, _, nameErr, _ := TestBrokersCommands(getBrokerListCmd, failArgs) 35 | assert.NotNil(t, nameErr) 36 | assert.Equal(t, "the cluster name is not specified or the cluster name is specified more than one", 37 | nameErr.Error()) 38 | } 39 | -------------------------------------------------------------------------------- /pkg/ctl/brokerstats/allocator_stats_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokerstats 19 | 20 | import ( 21 | "encoding/json" 22 | "testing" 23 | 24 | "github.com/apache/pulsar-client-go/pulsaradmin/pkg/utils" 25 | "github.com/stretchr/testify/assert" 26 | ) 27 | 28 | func TestDumpAllocatorStats(t *testing.T) { 29 | args := []string{"allocator-stats"} 30 | _, _, nameErr, _ := TestBrokerStatsCommands(dumpAllocatorStats, args) 31 | failOut := "the namespace name is not specified or the namespace name is specified more than one" 32 | assert.Equal(t, failOut, nameErr.Error()) 33 | 34 | successArgs := []string{"allocator-stats", "default"} 35 | statsOut, _, nameErr, _ := TestBrokerStatsCommands(dumpAllocatorStats, successArgs) 36 | assert.Nil(t, nameErr) 37 | 38 | var allocatorStats utils.AllocatorStats 39 | err := json.Unmarshal(statsOut.Bytes(), &allocatorStats) 40 | assert.Nil(t, err) 41 | assert.Equal(t, 0, allocatorStats.TinyCacheSize) 42 | assert.Equal(t, 256, allocatorStats.SmallCacheSize) 43 | assert.Equal(t, 64, allocatorStats.NormalCacheSize) 44 | } 45 | -------------------------------------------------------------------------------- /pkg/ctl/brokerstats/broker_stats.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokerstats 19 | 20 | import ( 21 | "github.com/spf13/cobra" 22 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 23 | ) 24 | 25 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 26 | resourceCmd := cmdutils.NewResourceCmd( 27 | "broker-stats", 28 | "Operations to collect broker statistics", 29 | "", 30 | "broker-stats") 31 | 32 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, dumpMonitoringMetrics) 33 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, dumpMBeans) 34 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, dumpTopics) 35 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, dumpAllocatorStats) 36 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, dumpLoadReport) 37 | 38 | return resourceCmd 39 | } 40 | -------------------------------------------------------------------------------- /pkg/ctl/brokerstats/load_report_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokerstats 19 | 20 | import ( 21 | "encoding/json" 22 | "testing" 23 | 24 | "github.com/apache/pulsar-client-go/pulsaradmin/pkg/utils" 25 | "github.com/stretchr/testify/assert" 26 | ) 27 | 28 | func TestDumpLoadReport(t *testing.T) { 29 | args := []string{"load-report"} 30 | loadReportOut, execErr, _, _ := TestBrokerStatsCommands(dumpLoadReport, args) 31 | if execErr != nil { 32 | t.FailNow() 33 | } 34 | getBrokerData := utils.LocalBrokerData{} 35 | err := json.Unmarshal(loadReportOut.Bytes(), &getBrokerData) 36 | if err != nil { 37 | t.FailNow() 38 | } 39 | defaultBrokerData := utils.NewLocalBrokerData() 40 | assert.Equal(t, defaultBrokerData, getBrokerData) 41 | } 42 | -------------------------------------------------------------------------------- /pkg/ctl/brokerstats/mbeans_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokerstats 19 | 20 | import ( 21 | "encoding/json" 22 | "testing" 23 | 24 | "github.com/apache/pulsar-client-go/pulsaradmin/pkg/utils" 25 | "github.com/stretchr/testify/assert" 26 | ) 27 | 28 | func TestDumpMBeans(t *testing.T) { 29 | args := []string{"mbeans"} 30 | mbeansOut, execErr, _, _ := TestBrokerStatsCommands(dumpMBeans, args) 31 | assert.Nil(t, execErr) 32 | 33 | var out []utils.Metrics 34 | err := json.Unmarshal(mbeansOut.Bytes(), &out) 35 | assert.Nil(t, err) 36 | 37 | value := out[0].Dimensions["MBean"] 38 | assert.Equal(t, true, len(value) > 0) 39 | } 40 | -------------------------------------------------------------------------------- /pkg/ctl/brokerstats/monitoring_metrics_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package brokerstats 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestDumpMonitoringMetrics(t *testing.T) { 28 | args := []string{"monitoring-metrics"} 29 | metricsOut, execErr, _, _ := TestBrokerStatsCommands(dumpMonitoringMetrics, args) 30 | assert.Nil(t, execErr) 31 | assert.True(t, strings.Contains(metricsOut.String(), "standalone")) 32 | } 33 | -------------------------------------------------------------------------------- /pkg/ctl/cluster/create_failure_domain_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package cluster 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestCreateFailureDomainCmdSuccess(t *testing.T) { 27 | args := []string{"create-failure-domain", "-b", "cluster-A", "standalone", "standalone-failure-domain"} 28 | _, execErr, NameErr, err := TestClusterCommands(createFailureDomainCmd, args) 29 | assert.Nil(t, execErr) 30 | assert.Nil(t, NameErr) 31 | assert.Nil(t, err) 32 | } 33 | 34 | func TestCreateFailureDomainCmdBrokerListError(t *testing.T) { 35 | args := []string{"create-failure-domain", "standalone", "standalone-failure-domain"} 36 | _, execErr, _, _ := TestClusterCommands(createFailureDomainCmd, args) 37 | assert.Equal(t, "broker list must be specified", execErr.Error()) 38 | } 39 | -------------------------------------------------------------------------------- /pkg/ctl/cluster/delete_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package cluster 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestDeleteClusterCmd(t *testing.T) { 28 | args := []string{"add", "delete-test"} 29 | _, _, _, err := TestClusterCommands(CreateClusterCmd, args) 30 | assert.Nil(t, err) 31 | 32 | args = []string{"list"} 33 | out, _, _, err := TestClusterCommands(ListClustersCmd, args) 34 | assert.Nil(t, err) 35 | clusters := out.String() 36 | assert.True(t, strings.Contains(clusters, "delete-test")) 37 | 38 | args = []string{"delete", "delete-test"} 39 | _, _, _, err = TestClusterCommands(deleteClusterCmd, args) 40 | assert.Nil(t, err) 41 | 42 | args = []string{"list"} 43 | out, _, _, err = TestClusterCommands(ListClustersCmd, args) 44 | assert.Nil(t, err) 45 | clusters = out.String() 46 | assert.False(t, strings.Contains(clusters, "delete-test")) 47 | } 48 | -------------------------------------------------------------------------------- /pkg/ctl/cluster/get_peer_clusters_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package cluster 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestGetPeerClustersCmd(t *testing.T) { 28 | args := []string{"add", "test_get_peer", "--peer-cluster", "standalone"} 29 | _, _, _, err := TestClusterCommands(CreateClusterCmd, args) 30 | if err != nil { 31 | t.Fatal(err) 32 | } 33 | 34 | args = []string{"gpc", "test_get_peer"} 35 | out, _, _, err := TestClusterCommands(getPeerClustersCmd, args) 36 | if err != nil { 37 | t.Fatal(err) 38 | } 39 | 40 | res := out.String() 41 | assert.True(t, strings.Contains(res, "standalone")) 42 | } 43 | -------------------------------------------------------------------------------- /pkg/ctl/cluster/get_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package cluster 19 | 20 | import ( 21 | "encoding/json" 22 | "regexp" 23 | "testing" 24 | 25 | "github.com/apache/pulsar-client-go/pulsaradmin/pkg/utils" 26 | "github.com/stretchr/testify/assert" 27 | ) 28 | 29 | func TestGetClusterData(t *testing.T) { 30 | args := []string{"get", "standalone"} 31 | out, _, _, err := TestClusterCommands(getClusterDataCmd, args) 32 | if err != nil { 33 | t.Error(err) 34 | } 35 | c := utils.ClusterData{} 36 | err = json.Unmarshal(out.Bytes(), &c) 37 | if err != nil { 38 | t.Error(err) 39 | } 40 | 41 | pulsarURL := regexp.MustCompile("^pulsar://[a-z-A-Z0-9]*:6650$") 42 | res := pulsarURL.MatchString(c.BrokerServiceURL) 43 | assert.True(t, res) 44 | 45 | httpURL := regexp.MustCompile("^http://[a-z-A-Z0-9]*:8080$") 46 | res = httpURL.MatchString(c.ServiceURL) 47 | assert.True(t, res) 48 | } 49 | -------------------------------------------------------------------------------- /pkg/ctl/cluster/update_peer_clusters_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package cluster 19 | 20 | import ( 21 | "encoding/json" 22 | "testing" 23 | 24 | "github.com/apache/pulsar-client-go/pulsaradmin/pkg/utils" 25 | "github.com/stretchr/testify/assert" 26 | ) 27 | 28 | func TestUpdatePeerClusters(t *testing.T) { 29 | args := []string{"add", "test_peer_cluster"} 30 | _, _, _, err := TestClusterCommands(CreateClusterCmd, args) 31 | if err != nil { 32 | t.Fatal(err) 33 | } 34 | 35 | args = []string{"update-peer-clusters", "-p", "test_peer_cluster", "standalone"} 36 | _, _, _, err = TestClusterCommands(updatePeerClustersCmd, args) 37 | if err != nil { 38 | t.Fatal(err) 39 | } 40 | 41 | args = []string{"get", "standalone"} 42 | out, _, _, _ := TestClusterCommands(getClusterDataCmd, args) 43 | 44 | var clusterData utils.ClusterData 45 | err = json.Unmarshal(out.Bytes(), &clusterData) 46 | if err != nil { 47 | t.Fatal(err) 48 | } 49 | 50 | peerCluster := clusterData.PeerClusterNames[0] 51 | assert.Equal(t, "test_peer_cluster", peerCluster) 52 | } 53 | -------------------------------------------------------------------------------- /pkg/ctl/context/context.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package context 19 | 20 | import ( 21 | "github.com/spf13/cobra" 22 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 23 | ) 24 | 25 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 26 | resourceCmd := cmdutils.NewResourceCmd( 27 | "context", 28 | "Interface for setting Pulsar Context ", 29 | "", 30 | "ctx", 31 | ) 32 | 33 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, currentContextCmd) 34 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, setContextCmd) 35 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, deleteContextCmd) 36 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getContextsCmd) 37 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, useContextCmd) 38 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, renameContextCmd) 39 | 40 | return resourceCmd 41 | } 42 | -------------------------------------------------------------------------------- /pkg/ctl/functionsworker/functions_worker.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package functionsworker 19 | 20 | import ( 21 | "github.com/spf13/cobra" 22 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 23 | ) 24 | 25 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 26 | resourceCmd := cmdutils.NewResourceCmd( 27 | "functions-worker", 28 | "Operations to collect function-worker statistics", 29 | "", 30 | "pfw", 31 | ) 32 | 33 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, functionsStats) 34 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, monitoringMetrics) 35 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getCluster) 36 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getClusterLeader) 37 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getFunctionAssignments) 38 | 39 | return resourceCmd 40 | } 41 | -------------------------------------------------------------------------------- /pkg/ctl/namespace/revoke_permission_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package namespace 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestRevokePermissionsArgsError(t *testing.T) { 27 | ns := "public/revoke-permissions-args-tests" 28 | 29 | args := []string{"revoke-permission", ns} 30 | _, _, _, err := TestNamespaceCommands(RevokePermissionsCmd, args) 31 | assert.NotNil(t, err) 32 | assert.Equal(t, "required flag(s) \"role\" not set", err.Error()) 33 | 34 | args = []string{"revoke-permission", "--role", "test-role"} 35 | _, _, nameErr, _ := TestNamespaceCommands(RevokePermissionsCmd, args) 36 | assert.NotNil(t, nameErr) 37 | assert.Equal(t, "the namespace name is not specified or the namespace name is specified more than one", 38 | nameErr.Error()) 39 | } 40 | -------------------------------------------------------------------------------- /pkg/ctl/namespace/revoke_subscription_permission_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package namespace 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestRevokeSubPermissionsArgsError(t *testing.T) { 27 | ns := "public/revoke-sub-permissions-args-tests" 28 | 29 | args := []string{"revoke-subscription-permission", ns} 30 | _, _, _, err := TestNamespaceCommands(RevokeSubPermissionsCmd, args) 31 | assert.NotNil(t, err) 32 | assert.Equal(t, "required flag(s) \"role\" not set", err.Error()) 33 | 34 | args = []string{"revoke-subscription-permission", "--role", "test-role"} 35 | _, _, nameErr, _ := TestNamespaceCommands(RevokeSubPermissionsCmd, args) 36 | assert.NotNil(t, nameErr) 37 | assert.Equal(t, "need to specified namespace name and subscription name", nameErr.Error()) 38 | } 39 | -------------------------------------------------------------------------------- /pkg/ctl/namespace/set_deduplication_status_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package namespace 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestDeduplicationStatus(t *testing.T) { 27 | args := []string{"create", "public/test-dedup-namespace"} 28 | createOut, _, _, err := TestNamespaceCommands(createNs, args) 29 | assert.Nil(t, err) 30 | assert.Equal(t, createOut.String(), "Created public/test-dedup-namespace successfully\n") 31 | 32 | args = []string{"set-deduplication", "public/test-dedup-namespace"} 33 | out, execErr, _, _ := TestNamespaceCommands(setDeduplication, args) 34 | assert.Nil(t, execErr) 35 | assert.Equal(t, out.String(), "Set deduplication is [false] successfully for public/test-dedup-namespace\n") 36 | 37 | args = []string{"set-deduplication", "public/test-dedup-namespace", "--enable"} 38 | out, execErr, _, _ = TestNamespaceCommands(setDeduplication, args) 39 | assert.Nil(t, execErr) 40 | assert.Equal(t, out.String(), "Set deduplication is [true] successfully for public/test-dedup-namespace\n") 41 | } 42 | -------------------------------------------------------------------------------- /pkg/ctl/nsisolationpolicy/ns_isolation_policy.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package nsisolationpolicy 19 | 20 | import ( 21 | "errors" 22 | 23 | "github.com/spf13/cobra" 24 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 25 | ) 26 | 27 | var checkNsIsolationPolicyArgs = func(args []string) error { 28 | if len(args) != 2 { 29 | return errors.New("need to specified the cluster name and the policy name") 30 | } 31 | return nil 32 | } 33 | 34 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 35 | resourceCmd := cmdutils.NewResourceCmd( 36 | "ns-isolation-policy", 37 | "Operations about namespace isolation policy", 38 | "", 39 | "ns-isolation-policy") 40 | 41 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getNsIsolationPolicy) 42 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getNsIsolationPolicies) 43 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, deleteNsIsolationPolicy) 44 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getBrokerWithPolicies) 45 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getAllBrokersWithPolicies) 46 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, setPolicy) 47 | 48 | return resourceCmd 49 | } 50 | -------------------------------------------------------------------------------- /pkg/ctl/packages/get_metadata_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package packages 19 | 20 | import ( 21 | "fmt" 22 | "path" 23 | "testing" 24 | 25 | "github.com/streamnative/pulsarctl/pkg/test" 26 | 27 | "github.com/stretchr/testify/assert" 28 | ) 29 | 30 | func TestPackagesGetMetadata(t *testing.T) { 31 | randomVersion := test.RandomSuffix() 32 | packageURL := fmt.Sprintf("function://public/default/get-metadata@%s", randomVersion) 33 | jarName := path.Join(ResourceDir(), "api-examples.jar") 34 | 35 | args := []string{"upload", 36 | packageURL, 37 | "--description", randomVersion, 38 | "--path", jarName, 39 | } 40 | 41 | output, execErr, err := TestPackagesCommands(uploadPackagesCmd, args) 42 | failImmediatelyIfErrorNotNil(t, execErr, err) 43 | assert.Equal(t, output.String(), 44 | fmt.Sprintf("The package '%s' uploaded from path '%s' successfully\n", packageURL, jarName)) 45 | 46 | args = []string{"get-metadata", 47 | packageURL, 48 | } 49 | 50 | output, execErr, err = TestPackagesCommands(getPackageMetadataCmd, args) 51 | failImmediatelyIfErrorNotNil(t, execErr, err) 52 | assert.Contains(t, output.String(), "description") 53 | } 54 | -------------------------------------------------------------------------------- /pkg/ctl/packages/packages.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package packages 19 | 20 | import ( 21 | "github.com/spf13/cobra" 22 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 23 | ) 24 | 25 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 26 | resourceCmd := cmdutils.NewResourceCmd( 27 | "packages", 28 | "Operations about packages", 29 | "") 30 | 31 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, listPackagesCmd) 32 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, listPackageVersionsCmd) 33 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, deletePackagesCmd) 34 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, getPackageMetadataCmd) 35 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, putPackageMetadataCmd) 36 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, downloadPackagesCmd) 37 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, uploadPackagesCmd) 38 | 39 | return resourceCmd 40 | } 41 | -------------------------------------------------------------------------------- /pkg/ctl/plugin/plugin.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package plugin 19 | 20 | import ( 21 | "github.com/spf13/cobra" 22 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 23 | ) 24 | 25 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 26 | resourceCmd := cmdutils.NewResourceCmd( 27 | "plugin", 28 | "Operations about plugins", 29 | "", 30 | "plugins") 31 | 32 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, listCmd) 33 | 34 | return resourceCmd 35 | } 36 | -------------------------------------------------------------------------------- /pkg/ctl/plugin/test_help.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package plugin 19 | 20 | import ( 21 | "bytes" 22 | 23 | "github.com/spf13/cobra" 24 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 25 | ) 26 | 27 | func testPluginCommands(newVerb func(*cmdutils.VerbCmd), args []string) (out *bytes.Buffer, 28 | execErr, err error) { 29 | 30 | cmdutils.ExecErrorHandler = func(err error) { 31 | execErr = err 32 | } 33 | rootCmd := &cobra.Command{} 34 | out = new(bytes.Buffer) 35 | rootCmd.SetOut(out) 36 | rootCmd.SetArgs(append([]string{"plugin"}, args...)) 37 | flagGrouping := cmdutils.NewGrouping() 38 | rootCmd.AddCommand(Command(flagGrouping)) 39 | resourceCmd := cmdutils.NewResourceCmd("plugin", "", "") 40 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, newVerb) 41 | err = rootCmd.Execute() 42 | return 43 | } 44 | -------------------------------------------------------------------------------- /pkg/ctl/resourcequotas/resource_quotas.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package resourcequotas 19 | 20 | import ( 21 | "github.com/spf13/cobra" 22 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 23 | ) 24 | 25 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 26 | resourceCmd := cmdutils.NewResourceCmd( 27 | "resource-quotas", 28 | "Operations about resource quotas", 29 | "", 30 | "resource-quotas") 31 | 32 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getResourceQuota) 33 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, setResourceQuota) 34 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, resetNamespaceBundleResourceQuota) 35 | 36 | return resourceCmd 37 | } 38 | -------------------------------------------------------------------------------- /pkg/ctl/sinks/create_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sinks 19 | 20 | import ( 21 | "os" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestCreateSinkFailedByEmptyFile(t *testing.T) { 28 | file, err := os.CreateTemp("", "test") 29 | if err != nil { 30 | t.Fatal(err) 31 | } 32 | defer func() { 33 | assert.NoError(t, os.Remove(file.Name())) 34 | }() 35 | 36 | failedArgs := []string{ 37 | "create", 38 | "--name", "failed-create", 39 | "--inputs", "failed-inputs", 40 | "--archive", file.Name(), 41 | } 42 | _, execErr, err := TestSinksCommands(createSinksCmd, failedArgs) 43 | failImmediatelyIfErrorNotNil(t, err) 44 | assert.NotNil(t, execErr) 45 | } 46 | 47 | func TestCreateSinkFailedByNotExistSinkConfigFile(t *testing.T) { 48 | failedArgs := []string{ 49 | "create", 50 | "--name", "failed-create", 51 | "--inputs", "failed-inputs", 52 | "--sink-config-file", "/tmp/failed-config.yaml", 53 | } 54 | _, execErr, err := TestSinksCommands(createSinksCmd, failedArgs) 55 | failImmediatelyIfErrorNotNil(t, err) 56 | assert.NotNil(t, execErr) 57 | } 58 | -------------------------------------------------------------------------------- /pkg/ctl/sinks/delete_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sinks 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestFailureDeleteSink(t *testing.T) { 28 | failureDeleteArgs := []string{"delete", 29 | "--name", "test-sink-delete", 30 | } 31 | 32 | exceptedErr := "Sink test-sink-delete doesn't exist" 33 | _, execErrMsg, _ := TestSinksCommands(deleteSinksCmd, failureDeleteArgs) 34 | assert.True(t, strings.Contains(execErrMsg.Error(), exceptedErr)) 35 | assert.NotNil(t, execErrMsg) 36 | 37 | nameNotExist := []string{"delete", 38 | "--name", "not-exist", 39 | } 40 | _, execErrMsg, _ = TestSinksCommands(deleteSinksCmd, nameNotExist) 41 | nameErr := "Sink not-exist doesn't exist" 42 | assert.True(t, strings.Contains(execErrMsg.Error(), nameErr)) 43 | } 44 | -------------------------------------------------------------------------------- /pkg/ctl/sinks/get_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sinks 19 | 20 | import ( 21 | "testing" 22 | "time" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestGetFailureSink(t *testing.T) { 28 | deleteArgs := []string{"delete", 29 | "--tenant", "public", 30 | "--namespace", "default", 31 | "--name", "bad-delete-sinks" + time.Now().String(), 32 | } 33 | 34 | _, execErr, err := TestSinksCommands(deleteSinksCmd, deleteArgs) 35 | if err != nil { 36 | t.Fatal(err) 37 | } 38 | assert.NotNil(t, execErr) 39 | 40 | failureGetArgs := []string{"get", 41 | "--name", "bad-get-sinks" + time.Now().String(), 42 | } 43 | _, execErr, err = TestSinksCommands(getSinksCmd, failureGetArgs) 44 | if err != nil { 45 | t.Fatal(err) 46 | } 47 | assert.NotNil(t, execErr) 48 | } 49 | -------------------------------------------------------------------------------- /pkg/ctl/sinks/list_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sinks 19 | 20 | import ( 21 | "testing" 22 | ) 23 | 24 | func TestListSinks(t *testing.T) { 25 | } 26 | -------------------------------------------------------------------------------- /pkg/ctl/sinks/restart_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sinks 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestRestartFailed(t *testing.T) { 27 | // test failure case 28 | failureArgs := []string{"restart", 29 | "--name", "not-exist", 30 | } 31 | _, execErr, err := TestSinksCommands(restartSinksCmd, failureArgs) 32 | if err != nil { 33 | t.Fatal(err) 34 | } 35 | assert.NotNil(t, execErr) 36 | } 37 | -------------------------------------------------------------------------------- /pkg/ctl/sinks/sinks.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sinks 19 | 20 | import ( 21 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 22 | 23 | "github.com/spf13/cobra" 24 | ) 25 | 26 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 27 | resourceCmd := cmdutils.NewResourceCmd( 28 | "sinks", 29 | "Interface for managing Pulsar IO sinks (egress data from Pulsar)", 30 | "", 31 | "sinks", 32 | ) 33 | 34 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, createSinksCmd) 35 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, updateSinksCmd) 36 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, deleteSinksCmd) 37 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, getSinksCmd) 38 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, listSinksCmd) 39 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, stopSinksCmd) 40 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, startSinksCmd) 41 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, restartSinksCmd) 42 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, statusSinksCmd) 43 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, listBuiltInSinksCmd) 44 | 45 | return resourceCmd 46 | } 47 | -------------------------------------------------------------------------------- /pkg/ctl/sinks/status_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sinks 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestFailureStatus(t *testing.T) { 28 | statusArgs := []string{"status", 29 | "--name", "not-exist", 30 | } 31 | 32 | _, execErr, err := TestSinksCommands(statusSinksCmd, statusArgs) 33 | if err != nil { 34 | t.Fatal(err) 35 | } 36 | 37 | errMsg := "Sink not-exist doesn't exist" 38 | assert.True(t, strings.Contains(execErr.Error(), errMsg)) 39 | } 40 | -------------------------------------------------------------------------------- /pkg/ctl/sinks/update_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sinks 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestUpdateSink(t *testing.T) { 28 | // test the sink name not exist 29 | failureUpdateArgs := []string{"update", 30 | "--name", "not-exist", 31 | } 32 | _, err, _ := TestSinksCommands(updateSinksCmd, failureUpdateArgs) 33 | assert.NotNil(t, err) 34 | assert.True(t, strings.Contains(err.Error(), "404")) 35 | } 36 | -------------------------------------------------------------------------------- /pkg/ctl/sources/create_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sources 19 | 20 | import ( 21 | "path" 22 | "strings" 23 | "testing" 24 | 25 | "github.com/streamnative/pulsarctl/pkg/test" 26 | "github.com/stretchr/testify/assert" 27 | ) 28 | 29 | func TestCreateSourceFailedByClassname(t *testing.T) { 30 | narName := path.Join(resourceDir(), "data-generator.nar") 31 | sourceName := "create-source-fail" + test.RandomSuffix() 32 | 33 | narFailArgs := []string{"create", 34 | "--tenant", "public", 35 | "--namespace", "default", 36 | "--name", sourceName, 37 | "--destination-topic-name", "my-topic", 38 | "--classname", "org.apache.pulsar.io.kafka.KafkaBytesSource", 39 | "--archive", narName, 40 | } 41 | 42 | narErrInfo := "Source class org.apache.pulsar.io.kafka.KafkaBytesSource must be in class path" 43 | narErrInfo2 := "Source class org.apache.pulsar.io.kafka.KafkaBytesSource not found in class loader" 44 | narOut, execErr, _ := TestSourcesCommands(createSourcesCmd, narFailArgs) 45 | assert.True(t, strings.Contains(narOut.String(), narErrInfo) || strings.Contains(narOut.String(), narErrInfo2)) 46 | assert.NotNil(t, execErr) 47 | } 48 | -------------------------------------------------------------------------------- /pkg/ctl/sources/delete_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sources 19 | 20 | import ( 21 | "testing" 22 | "time" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestFailureDeleteSource(t *testing.T) { 28 | failureDeleteArgs := []string{"delete", 29 | "--name", "bad-delete-sources-" + time.Now().String(), 30 | } 31 | 32 | _, execErr, err := TestSourcesCommands(deleteSourcesCmd, failureDeleteArgs) 33 | if err != nil { 34 | t.Fatal(err) 35 | } 36 | assert.NotNil(t, execErr) 37 | } 38 | -------------------------------------------------------------------------------- /pkg/ctl/sources/get_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sources 19 | 20 | import ( 21 | "testing" 22 | "time" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestGetFailureSource(t *testing.T) { 28 | failureGetArgs := []string{"get", 29 | "--name", "bad-get-sources-" + time.Now().String(), 30 | } 31 | _, execErr, err := TestSourcesCommands(getSourcesCmd, failureGetArgs) 32 | if err != nil { 33 | t.Fatal(err) 34 | } 35 | assert.NotNil(t, execErr) 36 | } 37 | -------------------------------------------------------------------------------- /pkg/ctl/sources/status_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sources 19 | 20 | import ( 21 | "testing" 22 | "time" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestFailureStatus(t *testing.T) { 28 | statusArgs := []string{"status", 29 | "--name", "bad-sources" + time.Now().String(), 30 | } 31 | 32 | _, execErr, err := TestSourcesCommands(statusSourcesCmd, statusArgs) 33 | if err != nil { 34 | t.Fatal(err) 35 | } 36 | assert.NotNil(t, execErr) 37 | } 38 | -------------------------------------------------------------------------------- /pkg/ctl/sources/update_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package sources 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestUpdateSource(t *testing.T) { 28 | // test the source name not exist 29 | failureUpdateArgs := []string{"update", 30 | "--name", "not-exist", 31 | } 32 | _, err, _ := TestSourcesCommands(updateSourcesCmd, failureUpdateArgs) 33 | assert.NotNil(t, err) 34 | failMsg := "Source not-exist doesn't exist" 35 | assert.True(t, strings.Contains(err.Error(), failMsg)) 36 | } 37 | -------------------------------------------------------------------------------- /pkg/ctl/status/check_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package status 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestStatusCheck(t *testing.T) { 28 | checkArgs := []string{"check"} 29 | out, err, _ := testStatusCommands(checkStatusCmd, checkArgs) 30 | assert.Nil(t, err) 31 | assert.True(t, strings.Contains(out.String(), "OK")) 32 | } 33 | -------------------------------------------------------------------------------- /pkg/ctl/status/status.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package status 19 | 20 | import ( 21 | "github.com/spf13/cobra" 22 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 23 | ) 24 | 25 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 26 | statusCmd := cmdutils.NewResourceCmd( 27 | "status", 28 | "Check service(broker or proxy) status", 29 | "", 30 | "status") 31 | cmdutils.AddVerbCmd(flagGrouping, statusCmd, checkStatusCmd) 32 | 33 | return statusCmd 34 | } 35 | -------------------------------------------------------------------------------- /pkg/ctl/status/test_help.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package status 19 | 20 | import ( 21 | "bytes" 22 | 23 | "github.com/spf13/cobra" 24 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 25 | ) 26 | 27 | func testStatusCommands(newVerb func(*cmdutils.VerbCmd), args []string) (out *bytes.Buffer, 28 | execErr, err error) { 29 | 30 | cmdutils.ExecErrorHandler = func(err error) { 31 | execErr = err 32 | } 33 | rootCmd := &cobra.Command{} 34 | out = new(bytes.Buffer) 35 | rootCmd.SetOut(out) 36 | rootCmd.SetArgs(append([]string{"status"}, args...)) 37 | flagGrouping := cmdutils.NewGrouping() 38 | rootCmd.AddCommand(Command(flagGrouping)) 39 | resourceCmd := cmdutils.NewResourceCmd( 40 | "status", 41 | "Check service(broker or proxy) status", 42 | "", 43 | "status") 44 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, newVerb) 45 | err = rootCmd.Execute() 46 | return 47 | } 48 | -------------------------------------------------------------------------------- /pkg/ctl/subscription/args_check.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package subscription 19 | 20 | import "github.com/pkg/errors" 21 | 22 | func CheckSubscriptionNameTwoArgs(args []string) error { 23 | if len(args) != 2 { 24 | return errors.New("need to specified the topic name and the subscription name") 25 | } 26 | 27 | return nil 28 | } 29 | -------------------------------------------------------------------------------- /pkg/ctl/subscription/list_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package subscription 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestListArgError(t *testing.T) { 27 | args := []string{"list"} 28 | _, _, nameErr, _ := TestSubCommands(ListCmd, args) 29 | assert.NotNil(t, nameErr) 30 | assert.Equal(t, "the topic name is not specified or the topic name is specified more than one", 31 | nameErr.Error()) 32 | } 33 | 34 | func TestListNonExistingTopicSub(t *testing.T) { 35 | args := []string{"list", "non-existing-topic"} 36 | _, execErr, _, _ := TestSubCommands(ListCmd, args) 37 | assert.NotNil(t, execErr) 38 | assert.Contains(t, execErr.Error(), "code: 404 reason: Topic") 39 | } 40 | -------------------------------------------------------------------------------- /pkg/ctl/subscription/subscription.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package subscription 19 | 20 | import ( 21 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 22 | 23 | "github.com/spf13/cobra" 24 | ) 25 | 26 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 27 | resourceCmd := cmdutils.NewResourceCmd( 28 | "subscriptions", 29 | "Operations about subscription(s)", 30 | "", 31 | "subscription", "subs", "sub") 32 | 33 | command := []func(cmd *cmdutils.VerbCmd){ 34 | CreateCmd, 35 | DeleteCmd, 36 | ListCmd, 37 | ExpireCmd, 38 | ResetCursorCmd, 39 | SkipCmd, 40 | PeekCmd, 41 | GetMessageByIDCmd, 42 | } 43 | 44 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, command...) 45 | 46 | return resourceCmd 47 | } 48 | -------------------------------------------------------------------------------- /pkg/ctl/token/test_help.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package token 19 | 20 | import ( 21 | "bytes" 22 | 23 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 24 | 25 | "github.com/spf13/cobra" 26 | ) 27 | 28 | func testTokenCommands(newVerb func(*cmdutils.VerbCmd), args []string) (out *bytes.Buffer, 29 | execErr, err error) { 30 | 31 | cmdutils.ExecErrorHandler = func(err error) { 32 | execErr = err 33 | } 34 | 35 | rootCmd := &cobra.Command{} 36 | out = new(bytes.Buffer) 37 | rootCmd.SetOut(out) 38 | rootCmd.SetArgs(append([]string{"token"}, args...)) 39 | flagGrouping := cmdutils.NewGrouping() 40 | rootCmd.AddCommand(Command(flagGrouping)) 41 | resourceCmd := cmdutils.NewResourceCmd("token", "", "") 42 | cmdutils.AddVerbCmd(flagGrouping, resourceCmd, newVerb) 43 | err = rootCmd.Execute() 44 | 45 | return 46 | } 47 | -------------------------------------------------------------------------------- /pkg/ctl/token/token.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package token 19 | 20 | import ( 21 | "github.com/streamnative/pulsarctl/pkg/cmdutils" 22 | 23 | "github.com/spf13/cobra" 24 | ) 25 | 26 | func Command(flagGrouping *cmdutils.FlagGrouping) *cobra.Command { 27 | resourceCmd := cmdutils.NewResourceCmd( 28 | "token", 29 | "Operations of token", 30 | "You can use this tool to generate secret key, private/public key, and token.", 31 | "") 32 | 33 | cmds := []func(*cmdutils.VerbCmd){ 34 | createKeyPair, 35 | createSecretKey, 36 | create, 37 | validate, 38 | show, 39 | } 40 | 41 | cmdutils.AddVerbCmds(flagGrouping, resourceCmd, cmds...) 42 | 43 | return resourceCmd 44 | } 45 | -------------------------------------------------------------------------------- /pkg/ctl/topic/args_check.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package topic 19 | 20 | import ( 21 | "github.com/pkg/errors" 22 | ) 23 | 24 | func CheckTopicNameTwoArgs(args []string) error { 25 | if len(args) != 2 { 26 | return errors.New("need to specified the topic name and the partitions") 27 | } 28 | 29 | return nil 30 | } 31 | -------------------------------------------------------------------------------- /pkg/ctl/topic/bundle_range_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package topic 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestGetBundleRangeCmd(t *testing.T) { 27 | args := []string{"create", "test-get-topic-bundle-range", "0"} 28 | _, execErr, _, _ := TestTopicCommands(CreateTopicCmd, args) 29 | assert.Nil(t, execErr) 30 | 31 | args = []string{"bundle-range", "test-get-topic-bundle-range"} 32 | out, execErr, _, _ := TestTopicCommands(GetBundleRangeCmd, args) 33 | assert.Nil(t, execErr) 34 | assert.Equal(t, "The bundle range of the topic "+ 35 | "persistent://public/default/test-get-topic-bundle-range is: 0xc0000000_0xffffffff\n", out.String()) 36 | } 37 | 38 | func TestGetBundleRangeArgError(t *testing.T) { 39 | args := []string{"bundle-range"} 40 | _, _, nameErr, _ := TestTopicCommands(GetBundleRangeCmd, args) 41 | assert.NotNil(t, nameErr) 42 | assert.Equal(t, "the topic name is not specified or the topic name is specified more than one", nameErr.Error()) 43 | } 44 | -------------------------------------------------------------------------------- /pkg/ctl/topic/compact_status_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package topic 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestCompactStatusArgsError(t *testing.T) { 27 | args := []string{"compact-status"} 28 | _, _, nameErr, _ := TestTopicCommands(StatusCmd, args) 29 | assert.NotNil(t, nameErr) 30 | assert.Equal(t, "the topic name is not specified or the topic name is specified more than one", nameErr.Error()) 31 | } 32 | 33 | func TestCompactStatusNonExistingTopicError(t *testing.T) { 34 | args := []string{"compact-status", "test-non-existing-compact-status"} 35 | _, execErr, _, _ := TestTopicCommands(StatusCmd, args) 36 | assert.NotNil(t, execErr) 37 | assert.Contains(t, execErr.Error(), "code: 404 reason: Topic") 38 | } 39 | 40 | func TestCompactStatusNonPersistentTopicError(t *testing.T) { 41 | args := []string{"compact-status", "non-persistent://public/default/test-non-persistent-topic-compact-status"} 42 | _, execErr, _, _ := TestTopicCommands(StatusCmd, args) 43 | assert.NotNil(t, execErr) 44 | assert.Equal(t, "need to provide a persistent topic", execErr.Error()) 45 | } 46 | -------------------------------------------------------------------------------- /pkg/ctl/topic/get_permissions_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package topic 19 | 20 | import ( 21 | "testing" 22 | 23 | "github.com/stretchr/testify/assert" 24 | ) 25 | 26 | func TestGetPermissionsArgError(t *testing.T) { 27 | args := []string{"get-permissions"} 28 | _, _, nameErr, _ := TestTopicCommands(GetPermissionsCmd, args) 29 | assert.NotNil(t, nameErr) 30 | assert.Equal(t, "the topic name is not specified or the topic name is specified more than one", nameErr.Error()) 31 | } 32 | -------------------------------------------------------------------------------- /pkg/ctl/topic/internal_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package topic 19 | 20 | import ( 21 | "strings" 22 | "testing" 23 | 24 | "github.com/stretchr/testify/assert" 25 | ) 26 | 27 | func TestGetInternalInfoArgError(t *testing.T) { 28 | args := []string{"internal-info"} 29 | _, _, nameErr, _ := TestTopicCommands(GetInternalInfoCmd, args) 30 | assert.NotNil(t, nameErr) 31 | assert.Equal(t, "the topic name is not specified or the topic name is specified more than one", nameErr.Error()) 32 | } 33 | 34 | func TestGetNonExistingTopicInternalInfo(t *testing.T) { 35 | args := []string{"internal-info", "non-existing-topic"} 36 | _, execErr, _, _ := TestTopicCommands(GetInternalInfoCmd, args) 37 | assert.NotNil(t, execErr) 38 | assert.True(t, strings.Contains(execErr.Error(), "code: 500")) 39 | } 40 | -------------------------------------------------------------------------------- /pkg/oauth2/os/os_interactor.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package os 19 | 20 | import ( 21 | "os/exec" 22 | "runtime" 23 | ) 24 | 25 | // Interactor abstracts opening a url on the users OS 26 | type Interactor interface { 27 | OpenURL(url string) error 28 | } 29 | 30 | // DefaultInteractor is the default OS interactor that wraps go standard os 31 | // package functionality to satisfy different interfaces 32 | type DefaultInteractor struct{} 33 | 34 | // OpenURL opens the passed in url in the default OS browser 35 | func (i *DefaultInteractor) OpenURL(url string) error { 36 | var cmd string 37 | var args []string 38 | 39 | switch runtime.GOOS { 40 | case "windows": 41 | cmd = "cmd" 42 | args = []string{"/c", "start"} 43 | case "darwin": 44 | cmd = "open" 45 | default: // "linux", "freebsd", "openbsd", "netbsd" 46 | cmd = "xdg-open" 47 | } 48 | args = append(args, url) 49 | return exec.Command(cmd, args...).Start() 50 | } 51 | -------------------------------------------------------------------------------- /pkg/pulsar/common/algorithm/ecdsa/es256.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package ecdsa 19 | 20 | import ( 21 | "crypto/ecdsa" 22 | "crypto/elliptic" 23 | "crypto/rand" 24 | 25 | "github.com/streamnative/pulsarctl/pkg/pulsar/common/algorithm/keypair" 26 | 27 | "github.com/pkg/errors" 28 | ) 29 | 30 | type ES256 struct{} 31 | 32 | func (h *ES256) GenerateSecret() ([]byte, error) { 33 | return nil, errors.New("unsupported operation") 34 | } 35 | 36 | func (h *ES256) GenerateKeyPair() (*keypair.KeyPair, error) { 37 | pri, err := ecdsa.GenerateKey(elliptic.P256(), rand.Reader) 38 | if err != nil { 39 | return nil, err 40 | } 41 | return keypair.New(keypair.ECDSA, pri), nil 42 | } 43 | -------------------------------------------------------------------------------- /pkg/pulsar/common/algorithm/ecdsa/es384.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package ecdsa 19 | 20 | import ( 21 | "crypto/ecdsa" 22 | "crypto/elliptic" 23 | "crypto/rand" 24 | 25 | "github.com/streamnative/pulsarctl/pkg/pulsar/common/algorithm/keypair" 26 | 27 | "github.com/pkg/errors" 28 | ) 29 | 30 | type ES384 struct{} 31 | 32 | func (h *ES384) GenerateSecret() ([]byte, error) { 33 | return nil, errors.New("unsupported operation") 34 | } 35 | 36 | func (h *ES384) GenerateKeyPair() (*keypair.KeyPair, error) { 37 | pri, err := ecdsa.GenerateKey(elliptic.P384(), rand.Reader) 38 | if err != nil { 39 | return nil, err 40 | } 41 | return keypair.New(keypair.ECDSA, pri), nil 42 | } 43 | -------------------------------------------------------------------------------- /pkg/pulsar/common/algorithm/ecdsa/es512.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package ecdsa 19 | 20 | import ( 21 | "crypto/ecdsa" 22 | "crypto/elliptic" 23 | "crypto/rand" 24 | 25 | "github.com/streamnative/pulsarctl/pkg/pulsar/common/algorithm/keypair" 26 | 27 | "github.com/pkg/errors" 28 | ) 29 | 30 | type ES512 struct{} 31 | 32 | func (h *ES512) GenerateSecret() ([]byte, error) { 33 | return nil, errors.New("unsupported operation") 34 | } 35 | 36 | func (h *ES512) GenerateKeyPair() (*keypair.KeyPair, error) { 37 | pri, err := ecdsa.GenerateKey(elliptic.P521(), rand.Reader) 38 | if err != nil { 39 | return nil, err 40 | } 41 | return keypair.New(keypair.ECDSA, pri), nil 42 | } 43 | -------------------------------------------------------------------------------- /pkg/pulsar/common/algorithm/hmac/hs256.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package hmac 19 | 20 | import ( 21 | "crypto/hmac" 22 | "crypto/rand" 23 | "crypto/sha256" 24 | 25 | "github.com/streamnative/pulsarctl/pkg/pulsar/common/algorithm/keypair" 26 | 27 | "github.com/pkg/errors" 28 | ) 29 | 30 | type HS256 struct{} 31 | 32 | func (h *HS256) GenerateSecret() ([]byte, error) { 33 | bytes := make([]byte, 32) 34 | if _, err := rand.Read(bytes); err != nil { 35 | return nil, err 36 | } 37 | s := hmac.New(sha256.New, bytes) 38 | return s.Sum(nil), nil 39 | } 40 | 41 | func (h *HS256) GenerateKeyPair() (*keypair.KeyPair, error) { 42 | return nil, errors.New("unsupported operation") 43 | } 44 | -------------------------------------------------------------------------------- /pkg/pulsar/common/algorithm/hmac/hs384.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package hmac 19 | 20 | import ( 21 | "crypto/hmac" 22 | "crypto/rand" 23 | "crypto/sha512" 24 | 25 | "github.com/streamnative/pulsarctl/pkg/pulsar/common/algorithm/keypair" 26 | 27 | "github.com/pkg/errors" 28 | ) 29 | 30 | type HS384 struct{} 31 | 32 | func (h *HS384) GenerateSecret() ([]byte, error) { 33 | bytes := make([]byte, 48) 34 | if _, err := rand.Read(bytes); err != nil { 35 | return nil, err 36 | } 37 | s := hmac.New(sha512.New384, bytes) 38 | return s.Sum(nil), nil 39 | } 40 | 41 | func (h *HS384) GenerateKeyPair() (*keypair.KeyPair, error) { 42 | return nil, errors.New("unsupported operation") 43 | } 44 | -------------------------------------------------------------------------------- /pkg/pulsar/common/algorithm/hmac/hs512.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package hmac 19 | 20 | import ( 21 | "crypto/hmac" 22 | "crypto/rand" 23 | "crypto/sha512" 24 | 25 | "github.com/streamnative/pulsarctl/pkg/pulsar/common/algorithm/keypair" 26 | 27 | "github.com/pkg/errors" 28 | ) 29 | 30 | type HS512 struct{} 31 | 32 | func (h *HS512) GenerateSecret() ([]byte, error) { 33 | bytes := make([]byte, 64) 34 | if _, err := rand.Read(bytes); err != nil { 35 | return nil, err 36 | } 37 | s := hmac.New(sha512.New, bytes) 38 | return s.Sum(nil), nil 39 | } 40 | 41 | func (h *HS512) GenerateKeyPair() (*keypair.KeyPair, error) { 42 | return nil, errors.New("unsupported operation") 43 | } 44 | -------------------------------------------------------------------------------- /pkg/pulsar/common/algorithm/rsa/rs256.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package rsa 19 | 20 | import ( 21 | "crypto/rand" 22 | "crypto/rsa" 23 | 24 | "github.com/streamnative/pulsarctl/pkg/pulsar/common/algorithm/keypair" 25 | 26 | "github.com/pkg/errors" 27 | ) 28 | 29 | type RS256 struct{} 30 | 31 | func (p *RS256) GenerateSecret() ([]byte, error) { 32 | return nil, errors.New("unsupported operation") 33 | } 34 | 35 | func (p *RS256) GenerateKeyPair() (*keypair.KeyPair, error) { 36 | pri, err := rsa.GenerateKey(rand.Reader, 2048) 37 | if err != nil { 38 | return nil, err 39 | } 40 | return keypair.New(keypair.RSA, pri), nil 41 | } 42 | -------------------------------------------------------------------------------- /pkg/pulsar/common/algorithm/rsa/rs384.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package rsa 19 | 20 | import ( 21 | "crypto/rand" 22 | "crypto/rsa" 23 | 24 | "github.com/streamnative/pulsarctl/pkg/pulsar/common/algorithm/keypair" 25 | 26 | "github.com/pkg/errors" 27 | ) 28 | 29 | type RS384 struct{} 30 | 31 | func (p *RS384) GenerateSecret() ([]byte, error) { 32 | return nil, errors.New("unsupported operation") 33 | } 34 | 35 | func (p *RS384) GenerateKeyPair() (*keypair.KeyPair, error) { 36 | pri, err := rsa.GenerateKey(rand.Reader, 3072) 37 | if err != nil { 38 | return nil, err 39 | } 40 | return keypair.New(keypair.RSA, pri), nil 41 | } 42 | -------------------------------------------------------------------------------- /pkg/pulsar/common/algorithm/rsa/rs512.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package rsa 19 | 20 | import ( 21 | "crypto/rand" 22 | "crypto/rsa" 23 | 24 | "github.com/streamnative/pulsarctl/pkg/pulsar/common/algorithm/keypair" 25 | 26 | "github.com/pkg/errors" 27 | ) 28 | 29 | type RS512 struct{} 30 | 31 | func (p *RS512) GenerateSecret() ([]byte, error) { 32 | return nil, errors.New("unsupported operation") 33 | } 34 | 35 | func (p *RS512) GenerateKeyPair() (*keypair.KeyPair, error) { 36 | pri, err := rsa.GenerateKey(rand.Reader, 4096) 37 | if err != nil { 38 | return nil, err 39 | } 40 | return keypair.New(keypair.RSA, pri), nil 41 | } 42 | -------------------------------------------------------------------------------- /pkg/test/bookkeeper/cluster_script.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookkeeper 19 | 20 | import "github.com/streamnative/pulsarctl/pkg/test" 21 | 22 | func InitBookieCluster(image, network, zookeeper string) *test.BaseContainer { 23 | bookieInit := test.NewContainer(image) 24 | bookieInit.WithNetwork([]string{network}) 25 | bookieInit.WithEnv(map[string]string{"BK_zkServers": zookeeper}) 26 | bookieInit.WithCmd([]string{"/opt/bookkeeper/bin/bookkeeper", "shell", "metaformat"}) 27 | bookieInit.WaitForLog("/opt/bookkeeper/bin/bookkeeper shell metaformat") 28 | return bookieInit 29 | } 30 | -------------------------------------------------------------------------------- /pkg/test/bookkeeper/cluster_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package bookkeeper 19 | 20 | import ( 21 | "context" 22 | "net/http" 23 | "testing" 24 | 25 | "github.com/stretchr/testify/assert" 26 | ) 27 | 28 | func TestDefaultCluster(t *testing.T) { 29 | ctx := context.Background() 30 | bkCluster, err := DefaultCluster() 31 | // nolint 32 | defer bkCluster.Close(ctx) 33 | if err != nil { 34 | t.Fatal(err) 35 | } 36 | err = bkCluster.Start(ctx) 37 | if err != nil { 38 | t.Fatal(err) 39 | } 40 | defer func() { 41 | assert.NoError(t, bkCluster.Stop(ctx)) 42 | }() 43 | 44 | path, err := bkCluster.GetHTTPServiceURL(ctx) 45 | if err != nil { 46 | t.Fatal(err) 47 | } 48 | 49 | resp, err := http.Get(path + "/api/v1/bookie/list_bookie_info") 50 | // nolint 51 | defer func() { 52 | assert.NoError(t, resp.Body.Close()) 53 | }() 54 | if err != nil { 55 | t.Fatal(err) 56 | } 57 | 58 | assert.Equal(t, 200, resp.StatusCode) 59 | } 60 | -------------------------------------------------------------------------------- /pkg/test/bookkeeper/containers/bookie.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package containers 19 | 20 | import "github.com/streamnative/pulsarctl/pkg/test" 21 | 22 | const ( 23 | BookieName = "bookie" 24 | DefaultBookieServicePort = 3181 25 | DefaultBookieHTTPServicePort = 8080 26 | ) 27 | 28 | func NewBookieContainer(image, network string) *test.BaseContainer { 29 | bk := test.NewContainer(image) 30 | bk.WithNetwork([]string{network}) 31 | bk.WithNetworkAliases(map[string][]string{network: {BookieName}}) 32 | bk.ExposedPorts([]string{"8080"}) 33 | bk.WithCmd([]string{"bookie"}) 34 | bk.WaitForPort("8080") 35 | return bk 36 | } 37 | -------------------------------------------------------------------------------- /pkg/test/bookkeeper/containers/zookeeper.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package containers 19 | 20 | import ( 21 | "fmt" 22 | 23 | "github.com/streamnative/pulsarctl/pkg/test" 24 | ) 25 | 26 | const ( 27 | ZookeeperName = "zookeeper" 28 | DefaultZookeeperServicePort = 2181 29 | ) 30 | 31 | func NewZookeeperContainer(image, network string) *test.BaseContainer { 32 | zookeeper := test.NewContainer(image) 33 | zookeeper.WithNetwork([]string{network}) 34 | zookeeper.WithNetworkAliases(map[string][]string{network: {ZookeeperName}}) 35 | zookeeper.WithCmd([]string{"zookeeper"}) 36 | zookeeper.WaitForLog("binding to port 0.0.0.0/0.0.0.0:2181") 37 | return zookeeper 38 | } 39 | 40 | func DefaultZookeeperServiceString() string { 41 | return fmt.Sprintf("%s:%d", ZookeeperName, DefaultZookeeperServicePort) 42 | } 43 | -------------------------------------------------------------------------------- /pkg/test/cluster.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package test 19 | 20 | import "context" 21 | 22 | type Cluster interface { 23 | // Start a cluster. 24 | Start(ctx context.Context) error 25 | 26 | // Stop a cluster. 27 | Stop(ctx context.Context) error 28 | 29 | // GetPlainTextServiceURL gets the service connect string. 30 | GetPlainTextServiceURL(ctx context.Context) (string, error) 31 | 32 | // GetHTTPServiceURL gets the HTTP service connect string. 33 | GetHTTPServiceURL(ctx context.Context) (string, error) 34 | 35 | // Close closes the resources used for starting cluster. 36 | Close(ctx context.Context) 37 | } 38 | -------------------------------------------------------------------------------- /pkg/test/pulsar/cluster_script.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package pulsar 19 | 20 | import ( 21 | "fmt" 22 | 23 | "github.com/streamnative/pulsarctl/pkg/test" 24 | ) 25 | 26 | // InitConf is a configuration for the initialization of the pulsar cluster. 27 | type InitConf struct { 28 | ClusterName string 29 | ConfigurationStore string 30 | Zookeeper string 31 | Broker string 32 | } 33 | 34 | // InitCluster returns a container for executing init pulsar cluster. 35 | func InitCluster(conf *InitConf, image, network string) *test.BaseContainer { 36 | pulsarInit := test.NewContainer(image) 37 | pulsarInit.WithNetwork([]string{network}) 38 | pulsarInit.WaitForLog(fmt.Sprintf("Cluster metadata for '%s' setup correctly", conf.ClusterName)) 39 | pulsarInit.WithCmd([]string{ 40 | "bash", "-c", 41 | fmt.Sprintf("bin/pulsar initialize-cluster-metadata -c %s -cs %s -uw %s -zk %s", 42 | conf.ClusterName, conf.ConfigurationStore, conf.Broker, conf.Zookeeper), 43 | }) 44 | return pulsarInit 45 | } 46 | -------------------------------------------------------------------------------- /pkg/test/pulsar/cluster_spec.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package pulsar 19 | 20 | // ClusterSpec is to build a pulsar cluster. 21 | type ClusterSpec struct { 22 | Image string 23 | ClusterName string 24 | BookiePort int 25 | NumBookies int 26 | BrokerServicePort int 27 | BrokerHTTPServicePort int 28 | NumBrokers int 29 | ProxyServicePort int 30 | ProxyHTTPServicePort int 31 | NumProxies int 32 | } 33 | 34 | // DefaultClusterSpec returns default configuration of a cluster. 35 | func DefaultClusterSpec() *ClusterSpec { 36 | return &ClusterSpec{ 37 | Image: LatestImage, 38 | ClusterName: "default-cluster", 39 | BookiePort: DefaultBookiePort, 40 | NumBookies: 2, 41 | BrokerServicePort: DefaultBrokerPort, 42 | BrokerHTTPServicePort: DefaultBrokerHTTPPort, 43 | NumBrokers: 2, 44 | ProxyServicePort: DefaultBrokerPort, 45 | ProxyHTTPServicePort: DefaultBrokerHTTPPort, 46 | NumProxies: 1, 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /pkg/test/pulsar/cluster_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package pulsar 19 | 20 | import ( 21 | "context" 22 | "net/http" 23 | "testing" 24 | 25 | "github.com/stretchr/testify/assert" 26 | ) 27 | 28 | func TestDefaultPulsarCluster(t *testing.T) { 29 | ctx := context.Background() 30 | pulsar, err := DefaultPulsarCluster() 31 | // nolint 32 | defer pulsar.Close(ctx) 33 | if err != nil { 34 | t.Fatal(err) 35 | } 36 | 37 | err = pulsar.Start(ctx) 38 | defer func() { 39 | assert.NoError(t, pulsar.Stop(ctx)) 40 | }() 41 | if err != nil { 42 | t.Fatal(err) 43 | } 44 | 45 | path, err := pulsar.GetHTTPServiceURL(ctx) 46 | if err != nil { 47 | t.Fatal(err) 48 | } 49 | 50 | resp, err := http.Get(path + "/admin/v2/tenants") 51 | // nolint 52 | defer func() { 53 | assert.NoError(t, resp.Body.Close()) 54 | }() 55 | if err != nil { 56 | t.Fatal(err) 57 | } 58 | 59 | assert.Equal(t, 200, resp.StatusCode) 60 | } 61 | -------------------------------------------------------------------------------- /pkg/test/pulsar/containers/bookie.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package containers 19 | 20 | import "github.com/streamnative/pulsarctl/pkg/test" 21 | 22 | const BookieName = "bookie" 23 | 24 | func NewBookieContainer(image, network string) *test.BaseContainer { 25 | bk := test.NewContainer(image) 26 | bk.WithNetwork([]string{network}) 27 | bk.WithNetworkAliases(map[string][]string{network: {BookieName}}) 28 | bk.WithCmd([]string{ 29 | "bash", "-c", 30 | "bin/apply-config-from-env.py conf/bookkeeper.conf && bin/pulsar bookie", 31 | }) 32 | bk.WaitForLog("Started component bookie-server") 33 | return bk 34 | } 35 | -------------------------------------------------------------------------------- /pkg/test/pulsar/containers/broker.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package containers 19 | 20 | import "github.com/streamnative/pulsarctl/pkg/test" 21 | 22 | const BrokerName = "broker" 23 | 24 | func NewBrokerContainer(image, network string) *test.BaseContainer { 25 | broker := test.NewContainer(image) 26 | broker.WithNetwork([]string{network}) 27 | broker.WithNetworkAliases(map[string][]string{network: {BrokerName}}) 28 | broker.ExposedPorts([]string{"8080", "6650"}) 29 | broker.WithCmd([]string{ 30 | "bash", "-c", 31 | "bin/apply-config-from-env.py conf/broker.conf && bin/pulsar broker", 32 | }) 33 | broker.WaitForPort("8080") 34 | return broker 35 | } 36 | -------------------------------------------------------------------------------- /pkg/test/pulsar/containers/proxy.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package containers 19 | 20 | import "github.com/streamnative/pulsarctl/pkg/test" 21 | 22 | const ProxyName = "proxy" 23 | 24 | func NewProxyContainer(image, network string) *test.BaseContainer { 25 | proxy := test.NewContainer(image) 26 | proxy.WithNetwork([]string{network}) 27 | proxy.WithNetworkAliases(map[string][]string{network: {ProxyName}}) 28 | proxy.ExposedPorts([]string{"8080", "6650"}) 29 | proxy.WithCmd([]string{ 30 | "bash", "-c", 31 | "bin/apply-config-from-env.py conf/proxy.conf && bin/pulsar proxy", 32 | }) 33 | proxy.WaitForLog("Server started at end point") 34 | return proxy 35 | } 36 | -------------------------------------------------------------------------------- /pkg/test/pulsar/containers/zookeeper.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package containers 19 | 20 | import "github.com/streamnative/pulsarctl/pkg/test" 21 | 22 | const ZookeeperName = "zookeeper" 23 | 24 | func NewZookeeperContainer(image, network string) *test.BaseContainer { 25 | zookeeper := test.NewContainer(image) 26 | zookeeper.WithNetwork([]string{network}) 27 | zookeeper.WithNetworkAliases(map[string][]string{network: {ZookeeperName}}) 28 | zookeeper.ExposedPorts([]string{"2181"}) 29 | zookeeper.WithCmd([]string{ 30 | "bin/pulsar", "zookeeper", 31 | }) 32 | zookeeper.WaitForPort("2181") 33 | return zookeeper 34 | } 35 | -------------------------------------------------------------------------------- /pkg/test/pulsar/standalone.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package pulsar 19 | 20 | import "github.com/streamnative/pulsarctl/pkg/test" 21 | 22 | func NewStandalone(image string) *test.BaseContainer { 23 | s := test.NewContainer(image) 24 | s.ExposedPorts([]string{"8080", "6650"}) 25 | s.WithCmd([]string{ 26 | "bin/pulsar", "standalone", 27 | }) 28 | s.WaitForPort("8080") 29 | return s 30 | } 31 | -------------------------------------------------------------------------------- /pkg/test/pulsar/standalone_test.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package pulsar 19 | 20 | import ( 21 | "context" 22 | "net/http" 23 | "testing" 24 | 25 | "github.com/stretchr/testify/assert" 26 | ) 27 | 28 | func TestNewStandalone(t *testing.T) { 29 | ctx := context.Background() 30 | standalone := NewStandalone("apachepulsar/pulsar:latest") 31 | err := standalone.Start(ctx) 32 | // nolint 33 | defer standalone.Stop(ctx) 34 | if err != nil { 35 | t.Fatal(err) 36 | } 37 | 38 | port, err := standalone.MappedPort(ctx, "8080") 39 | if err != nil { 40 | t.Fatal(err) 41 | } 42 | path := "http://localhost:" + port.Port() + "/admin/v2/tenants" 43 | 44 | resp, err := http.Get(path) 45 | // nolint 46 | defer resp.Body.Close() 47 | if err != nil { 48 | t.Fatal(err) 49 | } 50 | 51 | assert.Equal(t, 200, resp.StatusCode) 52 | 53 | } 54 | -------------------------------------------------------------------------------- /pkg/test/utils.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package test 19 | 20 | import ( 21 | "context" 22 | "math/rand" 23 | "os/exec" 24 | "time" 25 | 26 | "github.com/testcontainers/testcontainers-go" 27 | "github.com/testcontainers/testcontainers-go/network" 28 | ) 29 | 30 | // NewNetwork creates a network. 31 | func NewNetwork(name string) (*testcontainers.DockerNetwork, error) { 32 | ctx := context.Background() 33 | 34 | net, err := network.New(ctx, network.WithDriver(name)) 35 | return net, err 36 | } 37 | 38 | var letterRunes = []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ") 39 | 40 | func RandomSuffix() string { 41 | src := rand.NewSource(time.Now().UnixNano()) 42 | localRand := rand.New(src) 43 | b := make([]rune, 6) 44 | for i := range b { 45 | b[i] = letterRunes[localRand.Intn(len(letterRunes))] 46 | } 47 | return string(b) 48 | } 49 | 50 | func ExecCmd(containerID string, cmd []string) (string, error) { 51 | args := []string{"exec", containerID} 52 | args = append(args, cmd...) 53 | out, err := exec.Command("docker", args...).Output() 54 | return string(out), err 55 | } 56 | -------------------------------------------------------------------------------- /scripts/dev/__init__.py: -------------------------------------------------------------------------------- 1 | # Licensed to the Apache Software Foundation (ASF) under one 2 | # or more contributor license agreements. See the NOTICE file 3 | # distributed with this work for additional information 4 | # regarding copyright ownership. The ASF licenses this file 5 | # to you under the Apache License, Version 2.0 (the 6 | # "License"); you may not use this file except in compliance 7 | # with the License. You may obtain a copy of the License at 8 | # 9 | # http://www.apache.org/licenses/LICENSE-2.0 10 | # 11 | # Unless required by applicable law or agreed to in writing, 12 | # software distributed under the License is distributed on an 13 | # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | # KIND, either express or implied. See the License for the 15 | # specific language governing permissions and limitations 16 | # under the License. 17 | # -------------------------------------------------------------------------------- /scripts/dev/set-project-version.py: -------------------------------------------------------------------------------- 1 | # Licensed to the Apache Software Foundation (ASF) under one 2 | # or more contributor license agreements. See the NOTICE file 3 | # distributed with this work for additional information 4 | # regarding copyright ownership. The ASF licenses this file 5 | # to you under the Apache License, Version 2.0 (the 6 | # "License"); you may not use this file except in compliance 7 | # with the License. You may obtain a copy of the License at 8 | # 9 | # http://www.apache.org/licenses/LICENSE-2.0 10 | # 11 | # Unless required by applicable law or agreed to in writing, 12 | # software distributed under the License is distributed on an 13 | # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | # KIND, either express or implied. See the License for the 15 | # specific language governing permissions and limitations 16 | # under the License. 17 | 18 | #!/usr/bin/env python3 19 | 20 | import fileinput 21 | import glob 22 | import sys 23 | 24 | version = sys.argv[1] 25 | 26 | filename = glob.glob('./scripts/run-integration-tests.sh', recursive=True)[0] 27 | 28 | oldline = 'readonly PULSAR_DEFAULT_VERSION=' 29 | newline = '{}"{}"'.format(oldline, version) 30 | process = lambda l : newline + '\n' if l.count(oldline) else l 31 | 32 | lines = fileinput.input(files=(filename), inplace=True) 33 | 34 | for line in lines: 35 | print(process(line), end='') -------------------------------------------------------------------------------- /scripts/pulsar-service-shutdown.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | set -e 3 | 4 | readonly PULSAR_HOME=${PULSAR_HOME:-"/pulsar"} 5 | pushd ${PULSAR_HOME} 6 | echo "--- Stop the pulsar service ---" 7 | bin/pulsar-daemon stop standalone -force 8 | echo "--- Pulsar service is stopped ---" 9 | popd -------------------------------------------------------------------------------- /scripts/pulsar-service-startup.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | set -e 3 | 4 | readonly PULSAR_HOME=${PULSAR_HOME:-"/pulsar"} 5 | 6 | echo "--- Run pulsar service at the directory ${PULSAR_HOME} ---" 7 | pushd ${PULSAR_HOME} 8 | bin/apply-config-from-env.py conf/standalone.conf 9 | if [ ${FUNCTION_ENABLE} ]; then 10 | bin/pulsar-daemon start standalone 11 | else 12 | bin/pulsar-daemon start standalone -nss -nfw 13 | fi 14 | until curl http://localhost:8080/admin/v2/tenants > /dev/null 2>&1 15 | do 16 | sleep 1 17 | echo "Wait for pulsar service to be ready...$(date +%H:%M:%S)" 18 | done 19 | echo "--- Pulsar service is ready ---" 20 | popd -------------------------------------------------------------------------------- /scripts/run-integration-tests.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | set -e 3 | 4 | readonly PROJECT_ROOT=`cd $(dirname $0)/..; pwd` 5 | readonly IMAGE_NAME=pulsarctl-test 6 | readonly PULSAR_DEFAULT_VERSION="4.0.3" 7 | readonly PULSAR_VERSION=${PULSAR_VERSION:-${PULSAR_DEFAULT_VERSION}} 8 | 9 | docker build --build-arg PULSAR_VERSION=${PULSAR_VERSION} \ 10 | -t ${IMAGE_NAME} \ 11 | -f ${PROJECT_ROOT}/scripts/test-docker/Dockerfile ${PROJECT_ROOT} 12 | case ${1} in 13 | token) 14 | env_file=${PROJECT_ROOT}/test/auth/token.env 15 | docker run --rm --env-file ${env_file} -e TEST_ARGS=token ${IMAGE_NAME} 16 | ;; 17 | tls) 18 | env_file=${PROJECT_ROOT}/test/auth/tls.env 19 | docker run --rm --env-file ${env_file} -e TEST_ARGS=tls ${IMAGE_NAME} 20 | ;; 21 | function) 22 | docker run --name function --rm -e TEST_ARGS=function -e PULSAR_STANDALONE_USE_ZOOKEEPER=true -e FUNCTION_ENABLE=true ${IMAGE_NAME} 23 | ;; 24 | sink) 25 | docker run --name sink --rm -e TEST_ARGS=sink -e FUNCTION_ENABLE=true ${IMAGE_NAME} 26 | ;; 27 | source) 28 | docker run --name sink --rm -e TEST_ARGS=source -e FUNCTION_ENABLE=true ${IMAGE_NAME} 29 | ;; 30 | packages) 31 | docker run --name packages --rm -e TEST_ARGS=packages -e PULSAR_STANDALONE_USE_ZOOKEEPER=true -e PULSAR_PREFIX_enablePackagesManagement=true -e PULSAR_PREFIX_zookeeperServers=127.0.0.1:2181 ${IMAGE_NAME} 32 | ;; 33 | *) 34 | env_file=${PROJECT_ROOT}/test/policies/policies.env 35 | docker run --env-file ${env_file} ${IMAGE_NAME} 36 | ;; 37 | esac 38 | 39 | -------------------------------------------------------------------------------- /scripts/test-docker/Dockerfile: -------------------------------------------------------------------------------- 1 | ARG PULSAR_VERSION 2 | FROM apachepulsar/pulsar-all:$PULSAR_VERSION 3 | 4 | # use root user 5 | USER root 6 | 7 | # install required packages 8 | RUN apk update && apk add curl git build-base 9 | 10 | # install golang 11 | COPY --from=golang:1.24.0-alpine /usr/local/go/ /usr/local/go/ 12 | ENV PATH /usr/local/go/bin:$PATH 13 | 14 | 15 | # copy the code into image 16 | COPY . /pulsarctl 17 | 18 | # Create file for active status.html endpoint 19 | RUN mkdir -p /usr/local/apache && touch /usr/local/apache/htdocs 20 | 21 | ENV PULSAR_HOME /pulsar 22 | ENV PULSARCTL_HOME /pulsarctl 23 | 24 | ENTRYPOINT /pulsarctl/scripts/entrypoint.sh 25 | -------------------------------------------------------------------------------- /site/gen-pulsarctldocs/generators/package-lock.json: -------------------------------------------------------------------------------- 1 | { 2 | "lockfileVersion": 1 3 | } 4 | -------------------------------------------------------------------------------- /site/gen-pulsarctldocs/generators/v1_1/static_includes/_getting_started.md: -------------------------------------------------------------------------------- 1 | # GETTING STARTED 2 | 3 | This section contains the most basic commands for getting a workload 4 | running on your cluster. 5 | -------------------------------------------------------------------------------- /site/gen-pulsarctldocs/generators/v1_1/toc.yaml: -------------------------------------------------------------------------------- 1 | # 2 | # Licensed to the Apache Software Foundation (ASF) under one 3 | # or more contributor license agreements. See the NOTICE file 4 | # distributed with this work for additional information 5 | # regarding copyright ownership. The ASF licenses this file 6 | # to you under the Apache License, Version 2.0 (the 7 | # "License"); you may not use this file except in compliance 8 | # with the License. You may obtain a copy of the License at 9 | # 10 | # http://www.apache.org/licenses/LICENSE-2.0 11 | # 12 | # Unless required by applicable law or agreed to in writing, 13 | # software distributed under the License is distributed on an 14 | # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 15 | # KIND, either express or implied. See the License for the 16 | # specific language governing permissions and limitations 17 | # under the License. 18 | # 19 | 20 | categories: 21 | - name: GETTING STARTED 22 | include: _getting_started.md 23 | commands: 24 | - clusters 25 | - completion 26 | - functions 27 | - namespaces 28 | - schemas 29 | - sinks 30 | - sources 31 | - tenants 32 | - topics 33 | - brokers 34 | - broker-stats 35 | - subscriptions 36 | - resource-quotas 37 | - functions-worker 38 | - packages 39 | - ns-isolation-policy 40 | - token 41 | - context 42 | - bookkeeper 43 | - plugin 44 | - oauth2 45 | - status 46 | -------------------------------------------------------------------------------- /site/gen-pulsarctldocs/main.go: -------------------------------------------------------------------------------- 1 | // Licensed to the Apache Software Foundation (ASF) under one 2 | // or more contributor license agreements. See the NOTICE file 3 | // distributed with this work for additional information 4 | // regarding copyright ownership. The ASF licenses this file 5 | // to you under the Apache License, Version 2.0 (the 6 | // "License"); you may not use this file except in compliance 7 | // with the License. You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, 12 | // software distributed under the License is distributed on an 13 | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 14 | // KIND, either express or implied. See the License for the 15 | // specific language governing permissions and limitations 16 | // under the License. 17 | 18 | package main 19 | 20 | import ( 21 | "flag" 22 | 23 | "github.com/streamnative/pulsarctl/site/gen-pulsarctldocs/generators" 24 | ) 25 | 26 | func main() { 27 | flag.Parse() 28 | generators.GenerateFiles() 29 | } 30 | -------------------------------------------------------------------------------- /stable.txt: -------------------------------------------------------------------------------- 1 | v3.1.0.2 2 | -------------------------------------------------------------------------------- /test/auth/certs/broker-key.pem: -------------------------------------------------------------------------------- 1 | -----BEGIN PRIVATE KEY----- 2 | MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQCvv7ctmK2d9tqj 3 | E9RiD5i+HKKJIrpv1f0fZ+ORA5iAgQ7t2PZwfyw2aD1T6lg6ptWJZku9HldxE21L 4 | EeVApXaEJJJAWICWyR8sxFXro3lzcFw3montL7pr44J8aUoCVIuBXjy/TIrL6ixe 5 | g+e3EAhfglijidHakroqKO4wKD9brhBxlsfhEsWwGq1Eb0Q6EUqaPA+NBoB7NO8/ 6 | bPRexURUHsjdx4CFgNlo5sZTA3fh/hhhB3cFTO1ZvF1BOGrvXaGyYJjUSCiVAooO 7 | /c97G9IRzBAMUHPXzDhsg915JqqQyJuEhrxZ6WJp9JgbxIB4fqAagZ3S4WbdxMz8 8 | YwSs7Kc1AgMBAAECggEAAaWEK9MwXTiA1+JJrRmETtOp2isPIBkbI/4vLZ6hASM0 9 | ZpoPxQIMAf58BJs/dF03xu/EaeMs4oxSC9ABG9fxAk/tZtjta3w65Ip6W5jOfHxj 10 | AMpb3HMEBhq9kDjUTq1IGVAutYQcEMkC3WfS9e4ahfqMpguWgbu6LsbvZFgcL9mv 11 | pGnKv9YVe6Xk6isvqtq6G1af0rd7c//xF0i0e/qEo83Buok3gLEZOELZbcRxjUYc 12 | jnyglnXnwkGjuL4E3wgS3l73ZKsb6+AYoqhMPVz8t4/PN3tTrsBJKOSYo8KzIm0U 13 | ek9T8XmPbP0cuheRxp9Dp8TXJJQZK0N9jz+EL0ogQQKBgQDnavm8GpR4pap9cDOc 14 | +YI5s823b507pNdSU8elO9gLsP0JlFzv+sqghVko29r85D7Vn3MkgYTy0S4ANLCs 15 | 0NFDY8N2QH6U1dTkk1QXZydVZDuKJ5SSpC4v+Vafl8yDxhB4Nlxhbm9vJEMfLcXh 16 | 2kL6UlAuFDtYD0AdczwnHu5DjQKBgQDCauocm55FpcyDMMBO2CjurxcjBYS3S1xT 17 | Bz+sPtxJLjlKbAt8kSHUQcCcX9zhrQBfsT38LATCmKaOFqUW5/PPh2LcrxiMqlL1 18 | OJBUJ3Te2LTjlUn8r+DHv/69UIh5tchwRr3YgB0DuIs7jfmr4VfiOWTBtPVhoGFR 19 | 1Wt60j30SQKBgHzreS26J2VNAFBALgxRf6OIVMbtgDG/FOCDCyU9vazp+F2gcd61 20 | QYYPFYcBzx9uUiDctroBFHRCyJMh3jEbc6ruAogl3m6XUxmkEeOkMk5dEerM3N2f 21 | tLL+5Gy385U6aI+LwKhzhcG4EGeXPNdjC362ykNldnddnB2Jo/H2N2XNAoGAdnft 22 | xpbxP+GDGKIZXTIM5zzcLWQMdiC+1n1BSHVZiGJZWMczzKknYw7aDq+/iekApE79 23 | xW8RS373ZvfXi3i2Mcx+6pjrrbOQL4tTL2SHq8+DknaDCi4mG7IbyUKMlxW1WO1S 24 | e929UGogtZ6S+DCte9WbVwosyFuRUetpvgLk67kCgYBWetihZjgBWrqVYT24TTRH 25 | KxzSzH1JgzzF9qgTdlhXDv9hC+Kc0uTKsgViesDqVuCOjkwzY5OQr9c6duO0fwwP 26 | qNk/qltdgjMC5iiv7duyukfbEuqKEdGGer9HFb7en96dZdVQJpYHaaslAGurtD80 27 | ejCQZgzR2XaHSuIQb0IUVQ== 28 | -----END PRIVATE KEY----- 29 | -------------------------------------------------------------------------------- /test/auth/certs/client-key.pem: -------------------------------------------------------------------------------- 1 | -----BEGIN PRIVATE KEY----- 2 | MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDNQ32YQPmwW7yu 3 | 28ALrSaQluBiOO1osXBGO95E+RRRhhDrypDniOj5kYXg3bW0FLl444bVVG1o7BSS 4 | tPgiWwU97TElZQgFhMrmDCESWDLHGmCjT9JKnigZfEWEAIyJ3N6K5U+Ikcyk8YFF 5 | TH3C/+LBicYSc5XiNr3brotaaGqQUd4riF+qZ/So42PcvhmCzJ1/5o37gr4iAT1W 6 | EztbBLToxRjmLg36ukqN6MZaoVGaSmLXr920/OLVza6ZbFxhVgvXDBp3XPU6alS1 7 | njOsqXUomnav0HpXABuREzH9QoghRwUQAS9Zu8c62eFYTBtscbaY790DglijMtyQ 8 | obamHuELAgMBAAECggEBALGnokJuqiz7mTj2NSdl+6TVEOuyPbiJKpV/J4cm1XEh 9 | ye9qaTQcCRhH3UmcWrG75jM9KevloLRY8A1x1/lUMhtA+XJWGTU9k6a8BLut3nT4 10 | 3X87jNTMQgSczEXNe9WudmZcxhN7rVVtOOdTpt1pP0cnCWna5HTf0D8cuLvM975j 11 | r1YGTjKsCF1W+tp6ZAIIMfJkUI2qBRKvSxVCSs1vZBraox3yUVnq9oRLHxZZoqOd 12 | d51G5phRtn6ReVPBdT8fGUBEGg3jKxTu2/vLQMUyHy0hyCAM20gzOP4FIc2g+QZU 13 | y42byAuc89m0OrdRWsmzHCOxcq9DwY9npaz1RscR/2ECgYEA9bHJQ0Y1afpS5gn2 14 | KnXenRIw9oal1utQZnohCEJ4um+K/BCEHtDnI825LPNf34IKM2rSmssvHrYN51o0 15 | 92j9lHHXsf6MVluwsTsIu8MtNaJ1BLt96dub4ScGT6vvzObKTwsajUfIHk+FNsKq 16 | zps8yh1q0qyyfAcvR82+Xr6JIsMCgYEA1d+RHGewi/Ub/GCG99A1KFKsgbiIJnWB 17 | IFmrcyPWignhzDUcw2SV9XqAzeK8EOIHNq3e5U/tkA7aCWxtLb5UsQ8xvmwQY2cy 18 | X2XvSdIhO4K2PgRLgjlzZ8RHSULglqyjB2i6TjwjFl8TsRzYr6JlV6+2cMujw4Bl 19 | g3a8gz071BkCgYBLP7BMkmw5kRliqxph1sffg3rLhmG0eU2elTkYtoMTVqZSnRxZ 20 | 89FW/eMBCWkLo2BMbyMhlalQ1qFbgh1GyTkhBdzx/uwsZtiu7021dAmcq6z7ThE6 21 | VrBfPPyJ2jcPon/DxbrUGnAIGILMSsLVlGYB4RCehZYEto6chz8O9Xw60QKBgCnd 22 | us1BqviqwZC04JbQJie/j09RbS2CIQXRJ9PBNzUMXCwaVYgWP5ivI1mqQcBYTqsw 23 | fAqNi+aAUcQ4emLS+Ec0vzsUclzTDbRJAv+DZ8f7fWtEcfeLAYFVldLMiaRVJRDF 24 | OnsoIII3mGY6TFyNQKNanS8VXfheQQDsFFjoera5AoGBALXYEXkESXpw4LT6qJFz 25 | ktQuTZDfS6LtR14/+NkYL9c5wBC4Otkg4bNbT8xGlUjethRfpkm8xRTB6zfC1/p/ 26 | Cg6YU1cwqlkRurAhE3PEv1dCc1IDbzou8xnwqHrd6sGPDQmQ3aEtU5eJhDZKIZfx 27 | nQqPGK92+Jtne7+W1mFZooxs 28 | -----END PRIVATE KEY----- 29 | -------------------------------------------------------------------------------- /test/auth/tls.env: -------------------------------------------------------------------------------- 1 | PULSAR_PREFIX_tlsEnabled=true 2 | PULSAR_PREFIX_tlsCertificateFilePath=/pulsarctl/test/auth/certs/broker-cert.pem 3 | PULSAR_PREFIX_tlsKeyFilePath=/pulsarctl/test/auth/certs/broker-key.pem 4 | PULSAR_PREFIX_tlsTrustCertsFilePath=/pulsarctl/test/auth/certs/cacert.pem 5 | PULSAR_PREFIX_tlsAllowInsecureConnection=false 6 | PULSAR_PREFIX_brokerServicePortTls=6651 7 | PULSAR_PREFIX_webServicePortTls=8443 -------------------------------------------------------------------------------- /test/auth/token.env: -------------------------------------------------------------------------------- 1 | authenticationEnabled=true 2 | authenticationProviders=org.apache.pulsar.broker.authentication.AuthenticationProviderToken 3 | authorizationEnabled=true 4 | authorizationProvider=org.apache.pulsar.broker.authorization.PulsarAuthorizationProvider 5 | brokerClientAuthenticationPlugin=org.apache.pulsar.client.impl.auth.AuthenticationToken 6 | brokerClientAuthenticationParameters=token:eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJ0ZXN0LXVzZXIifQ.Yb52IE0B5wzooAdSlIlskEgb6_HBXST8k3lINZS5wwg 7 | superUserRoles=admin 8 | PULSAR_PREFIX_tokenSecretKey=file:///pulsarctl/test/auth/token/secret.key -------------------------------------------------------------------------------- /test/auth/token/secret.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/auth/token/secret.key -------------------------------------------------------------------------------- /test/client.conf: -------------------------------------------------------------------------------- 1 | # 2 | # Licensed to the Apache Software Foundation (ASF) under one 3 | # or more contributor license agreements. See the NOTICE file 4 | # distributed with this work for additional information 5 | # regarding copyright ownership. The ASF licenses this file 6 | # to you under the Apache License, Version 2.0 (the 7 | # "License"); you may not use this file except in compliance 8 | # with the License. You may obtain a copy of the License at 9 | # 10 | # http://www.apache.org/licenses/LICENSE-2.0 11 | # 12 | # Unless required by applicable law or agreed to in writing, 13 | # software distributed under the License is distributed on an 14 | # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 15 | # KIND, either express or implied. See the License for the 16 | # specific language governing permissions and limitations 17 | # under the License. 18 | # 19 | 20 | # Pulsar Client configuration 21 | webServiceUrl=https://localhost:8443/ 22 | tlsAllowInsecureConnection=false 23 | tlsTrustCertsFilePath=/test/auth/certs/cacert.pem 24 | authParams=tlsCertFile:/test/auth/certs/client-cert.pem,tlsKeyFile:/test/auth/certs/client-key.pem 25 | 26 | -------------------------------------------------------------------------------- /test/docker/docker-compose.yml: -------------------------------------------------------------------------------- 1 | version: '3' 2 | services: 3 | zookeeper: 4 | container_name: bk-zookeeper 5 | image: "apache/bookkeeper:4.16.3" 6 | hostname: zookeeper 7 | entrypoint: 8 | - /bin/bash 9 | - /opt/bookkeeper/scripts/entrypoint.sh 10 | - zookeeper 11 | bookie: 12 | container_name: bk 13 | depends_on: 14 | - zookeeper 15 | - bookie-init 16 | image: "apache/bookkeeper:4.16.3" 17 | hostname: bookie 18 | links: 19 | - zookeeper 20 | ports: 21 | - "8080:8080" 22 | environment: 23 | - BK_zkServers=zookeeper:2181 24 | - BK_httpServerEnabled=true 25 | - BK_httpServerPort=8080 26 | - BK_httpServerClass=org.apache.bookkeeper.http.vertx.VertxHttpServer 27 | - BK_ledgerDirectories=bk/ledgers 28 | - BK_indexDirectories=bk/ledgers 29 | - BK_journalDirectory=bk/journal 30 | command: 31 | - | 32 | /opt/bookkeeper/bin/bookkeeper bookie 33 | restart: on-failure 34 | bookie-init: 35 | image: "apache/bookkeeper:4.16.3" 36 | hostname: bookie-client 37 | links: 38 | - zookeeper 39 | environment: 40 | - BK_zkServers=zookeeper:2181 41 | command: 42 | - | 43 | /opt/bookkeeper/bin/bookkeeper shell metaformat 44 | -------------------------------------------------------------------------------- /test/functions/example-function-config.yaml: -------------------------------------------------------------------------------- 1 | # 2 | # Licensed to the Apache Software Foundation (ASF) under one 3 | # or more contributor license agreements. See the NOTICE file 4 | # distributed with this work for additional information 5 | # regarding copyright ownership. The ASF licenses this file 6 | # to you under the Apache License, Version 2.0 (the 7 | # "License"); you may not use this file except in compliance 8 | # with the License. You may obtain a copy of the License at 9 | # 10 | # http://www.apache.org/licenses/LICENSE-2.0 11 | # 12 | # Unless required by applicable law or agreed to in writing, 13 | # software distributed under the License is distributed on an 14 | # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 15 | # KIND, either express or implied. See the License for the 16 | # specific language governing permissions and limitations 17 | # under the License. 18 | # 19 | 20 | tenant: "public" 21 | namespace: "default" 22 | name: "example-functions-config" 23 | className: "org.apache.pulsar.functions.api.examples.ExclamationFunction" 24 | inputs: ["test_src"] 25 | output: "test_result" 26 | autoAck: true 27 | parallelism: 1 28 | secrets: 29 | stringKey: "stringSecret" 30 | mapKey: 31 | path: "secret" 32 | key: "password" 33 | arrayMapKey: 34 | - path: "secret2" 35 | key: "password2" 36 | userConfig: 37 | stringKey: "stringValue" 38 | mapKey: 39 | path: "config" 40 | key: "value" 41 | arrayMapKey: 42 | - path: "config2" 43 | key: "value2" 44 | -------------------------------------------------------------------------------- /test/functions/example-update-function-config.yaml: -------------------------------------------------------------------------------- 1 | # 2 | # Licensed to the Apache Software Foundation (ASF) under one 3 | # or more contributor license agreements. See the NOTICE file 4 | # distributed with this work for additional information 5 | # regarding copyright ownership. The ASF licenses this file 6 | # to you under the Apache License, Version 2.0 (the 7 | # "License"); you may not use this file except in compliance 8 | # with the License. You may obtain a copy of the License at 9 | # 10 | # http://www.apache.org/licenses/LICENSE-2.0 11 | # 12 | # Unless required by applicable law or agreed to in writing, 13 | # software distributed under the License is distributed on an 14 | # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 15 | # KIND, either express or implied. See the License for the 16 | # specific language governing permissions and limitations 17 | # under the License. 18 | # 19 | 20 | secrets: 21 | stringKey: "stringSecret" 22 | mapKey: 23 | path: "secret" 24 | key: "password" 25 | arrayMapKey: 26 | - path: "secret2" 27 | key: "password2" 28 | userConfig: 29 | stringKey: "stringValue" 30 | mapKey: 31 | path: "config" 32 | key: "value" 33 | arrayMapKey: 34 | - path: "config2" 35 | key: "value2" 36 | -------------------------------------------------------------------------------- /test/key/pulsar-admin-es256-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-es256-private.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-es256-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-es256-public.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-es384-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-es384-private.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-es384-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-es384-public.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-es512-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-es512-private.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-es512-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-es512-public.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-hs256-base64-secret.key: -------------------------------------------------------------------------------- 1 | gw0EWY5wkfWir8Yx0E7U0Uqc31oX/ep8LPAyjE76Bbs= -------------------------------------------------------------------------------- /test/key/pulsar-admin-hs256-secret.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-hs256-secret.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-hs384-base64-secret.key: -------------------------------------------------------------------------------- 1 | uMYzvffcfU5cmfKfe4qkTIVrWOoJvFFSoU6jQNzZ5oeG4HNWkLcS/6yolh0mH829 -------------------------------------------------------------------------------- /test/key/pulsar-admin-hs384-secret.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-hs384-secret.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-hs512-base64-secret.key: -------------------------------------------------------------------------------- 1 | QzPjJYTz+kPpgWGdSlEzV8IczfG0CvFRyB1Mo5LdmQ+5iynvsOJ1B0XihyQGBGpjUAzv9WgERRToVnaBxei6OA== -------------------------------------------------------------------------------- /test/key/pulsar-admin-hs512-secret.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-hs512-secret.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-rs256-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-rs256-private.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-rs256-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-rs256-public.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-rs384-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-rs384-private.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-rs384-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-rs384-public.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-rs512-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-rs512-private.key -------------------------------------------------------------------------------- /test/key/pulsar-admin-rs512-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsar-admin-rs512-public.key -------------------------------------------------------------------------------- /test/key/pulsarctl-es256-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-es256-private.key -------------------------------------------------------------------------------- /test/key/pulsarctl-es256-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-es256-public.key -------------------------------------------------------------------------------- /test/key/pulsarctl-es384-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-es384-private.key -------------------------------------------------------------------------------- /test/key/pulsarctl-es384-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-es384-public.key -------------------------------------------------------------------------------- /test/key/pulsarctl-es512-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-es512-private.key -------------------------------------------------------------------------------- /test/key/pulsarctl-es512-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-es512-public.key -------------------------------------------------------------------------------- /test/key/pulsarctl-hs256-base64-secret.key: -------------------------------------------------------------------------------- 1 | JD+/yu4BlzQtFQhAKRBTKXld9mnaN57B9MTmLEj8AwY= -------------------------------------------------------------------------------- /test/key/pulsarctl-hs256-secret.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-hs256-secret.key -------------------------------------------------------------------------------- /test/key/pulsarctl-hs384-base64-secret.key: -------------------------------------------------------------------------------- 1 | ciMGLZlC8Vw04klH4Sb1JWS7Mk9EnfEdxzljlgNVKkoSirBKTDDl+ju9I1owZox6 -------------------------------------------------------------------------------- /test/key/pulsarctl-hs384-secret.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-hs384-secret.key -------------------------------------------------------------------------------- /test/key/pulsarctl-hs512-base64-secret.key: -------------------------------------------------------------------------------- 1 | Aq+Z16gFiFWgxGTPNVRbIoS2VqwC4L9X/03XB36sh7lswqvdvdazu9DMiMi1Rz/XqinNkOplR4XVwIiVF19VLg== -------------------------------------------------------------------------------- /test/key/pulsarctl-hs512-secret.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-hs512-secret.key -------------------------------------------------------------------------------- /test/key/pulsarctl-rs256-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-rs256-private.key -------------------------------------------------------------------------------- /test/key/pulsarctl-rs256-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-rs256-public.key -------------------------------------------------------------------------------- /test/key/pulsarctl-rs384-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-rs384-private.key -------------------------------------------------------------------------------- /test/key/pulsarctl-rs384-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-rs384-public.key -------------------------------------------------------------------------------- /test/key/pulsarctl-rs512-private.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-rs512-private.key -------------------------------------------------------------------------------- /test/key/pulsarctl-rs512-public.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/streamnative/pulsarctl/5b322f693b0bba2891d6e121e5c96b61a002c9bf/test/key/pulsarctl-rs512-public.key -------------------------------------------------------------------------------- /test/policies/policies.env: -------------------------------------------------------------------------------- 1 | systemTopicEnabled=true 2 | topicLevelPoliciesEnabled=true -------------------------------------------------------------------------------- /test/script/check.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | 3 | # Waiting bookie HTTP service start up, if the bookie HTTP service does not 4 | # start up in 30 seconds, that means the bookie HTTP service is not start 5 | # up successfully. 6 | function checkBookieHTTP() { 7 | failed=0 8 | until curl localhost:8080; do 9 | echo waiting service start... 10 | failed=`expr ${failed} + 1` 11 | if [[ ${failed} == 30 ]]; then 12 | echo service start up was failed 13 | exit 1 14 | fi 15 | sleep 1 16 | done 17 | } 18 | 19 | function checkFunctionWorker() { 20 | failed=0 21 | until curl localhost:8080/admin/v2/persistent/public/functions/coordinate/stats; do 22 | echo "waiting function worker service start..." 23 | failed=`expr ${failed} + 1` 24 | if [[ ${failed} == 30 ]]; then 25 | echo "function worker service start up was failed" 26 | exit 1 27 | fi 28 | sleep 1 29 | done 30 | } 31 | 32 | case $1 in 33 | bookieHTTP) checkBookieHTTP 34 | ;; 35 | functionWorker) checkFunctionWorker 36 | ;; 37 | *) echo Which service you would like to check? 38 | echo Available service: bookieHTTP, functionWorker 39 | ;; 40 | esac --------------------------------------------------------------------------------