diff --git a/integration_oidc_setup.sh b/integration_oidc_setup.sh index 818e54961..915eb5498 100755 --- a/integration_oidc_setup.sh +++ b/integration_oidc_setup.sh @@ -40,6 +40,8 @@ help() { echo -e "\t OP_USE_LOGIN_TOKEN \t Use first access token obtained by IDP (true/false). Default: false" echo -e "\t OP_STORAGE_AUDIENCE \t Name of the storage audience (Not required when using 'OP_USE_LOGIN_TOKEN=true')" echo -e "\t OP_STORAGE_SCOPE \t Scope for token exchange (Not required when using 'OP_USE_LOGIN_TOKEN=true')" + echo -e "" + echo -e "CONVERT_EXISTING_CONNECTION \t\t Convert existing connection between OpenProject and Nextcloud (true/false)" } log_error() { @@ -91,14 +93,20 @@ else fi # Validate required configs for integration setup -if [[ -z $NC_INTEGRATION_PROVIDER_TYPE ]] || - [[ -z $NC_INTEGRATION_ENABLE_NAVIGATION ]] || - [[ -z $NC_INTEGRATION_ENABLE_SEARCH ]]; then - log_error "Following configs are required for integration setup:\n NC_INTEGRATION_ENABLE_NAVIGATION\n NC_INTEGRATION_ENABLE_SEARCH\n NC_INTEGRATION_PROVIDER_TYPE" +if [[ -z $NC_INTEGRATION_PROVIDER_TYPE ]]; then + log_error "NC_INTEGRATION_PROVIDER_TYPE is required." help exit 1 fi +if [[ $CONVERT_EXISTING_CONNECTION != "true" ]]; then + if [[ -z $NC_INTEGRATION_ENABLE_NAVIGATION ]] || [[ -z $NC_INTEGRATION_ENABLE_SEARCH ]]; then + log_error "Following configs are required for integration setup:\n NC_INTEGRATION_ENABLE_NAVIGATION\n NC_INTEGRATION_ENABLE_SEARCH" + help + exit 1 + fi +fi + if [[ $NC_INTEGRATION_PROVIDER_TYPE == "nextcloud_hub" ]]; then if [[ -z $NC_INTEGRATION_OP_CLIENT_ID ]] || [[ -z $NC_INTEGRATION_OP_CLIENT_SECRET ]]; then log_info "You can provide the following environment variables to create the predefined OIDC client:\n 'NC_INTEGRATION_OP_CLIENT_ID'\n 'NC_INTEGRATION_OP_CLIENT_SECRET'" @@ -380,13 +388,12 @@ if [[ "$openproject_version" < "$OP_MINIMUM_VERSION" ]]; then exit 1 fi -# API call to add storage -cat >${INTEGRATION_SETUP_TEMP_DIR}/request_body_4_op_create_storage.json <${INTEGRATION_SETUP_TEMP_DIR}/request_body_4_op_create_storage.json < ${INTEGRATION_SETUP_TEMP_DIR}/get_op_storage_req_data.json + update_storage_response=$(setup_op_storage "PATCH" "$OP_STORAGE_ID" | tail -n1) + if [[ ${update_storage_response} != 200 ]]; then + log_error "Failed to update existing OpenProject storage" + exit 1 + else + log_success "Successfully updated existing OpenProject storage" + fi + + if [[ $INTEGRATION_SETUP_DEBUG != "true" ]]; then rm ${INTEGRATION_SETUP_TEMP_DIR}/get_op_storage_req_data.json; fi + + if [[ $NC_INTEGRATION_PROVIDER_TYPE == "nextcloud_hub" ]]; then + createOidcClient + get_nc_integration_update_data | + jq --arg client_id "$NC_INTEGRATION_OP_CLIENT_ID" \ + '.values.targeted_audience_client_id = $client_id' \ + > "${INTEGRATION_SETUP_TEMP_DIR}/request_body_for_converting_existing_setup.json" + + nc_integration_update_response=$(setup_nc_integration "PATCH" request_body_for_converting_existing_setup.json | tail -n1) + if [[ ${nc_integration_update_response} == 200 ]]; then + log_success "Successfully updated existing Nextcloud integration setup to Nextcloud hub OIDC provider setup" + else + log_error "Failed to update existing Nextcloud integration setup to Nextcloud hub OIDC provider setup" + exit 1 + fi + elif [[ $NC_INTEGRATION_PROVIDER_TYPE == "external" ]]; then + get_nc_integration_update_data | + jq --arg provider_name "$NC_INTEGRATION_PROVIDER_NAME" \ + '.values.oidc_provider = $provider_name' \ + > "${INTEGRATION_SETUP_TEMP_DIR}/request_body_for_converting_existing_setup.json" + + nc_integration_update_response=$(setup_nc_integration "PATCH" request_body_for_converting_existing_setup.json | tail -n1) + if [[ ${nc_integration_update_response} == 200 ]]; then + log_success "Successfully updated existing Nextcloud integration setup to external OIDC provider setup" + else + log_error "Failed to update existing Nextcloud integration setup to external OIDC provider setup" + exit 1 + fi + fi + + if [[ $INTEGRATION_SETUP_DEBUG != "true" ]]; then rm ${INTEGRATION_SETUP_TEMP_DIR}/request_body_for_converting_existing_setup.json; fi + exit 0 +fi -if [[ $INTEGRATION_SETUP_DEBUG != "true" ]]; then rm ${INTEGRATION_SETUP_TEMP_DIR}/request_body_4_op_create_storage.json; fi +# API call to add storage +get_op_storage_req_data | jq '.applicationPassword = ""' > ${INTEGRATION_SETUP_TEMP_DIR}/get_op_storage_req_data.json +op_storage_create_response=$(setup_op_storage "POST" | sed '$d') + +if [[ $INTEGRATION_SETUP_DEBUG != "true" ]]; then rm ${INTEGRATION_SETUP_TEMP_DIR}/get_op_storage_req_data.json; fi # check for errors -response_type=$(echo $create_storage_response | jq -r "._type") +response_type=$(echo $op_storage_create_response | jq -r "._type") if [[ ${response_type} == "Error" ]]; then - error_message=$(echo $create_storage_response | jq -r ".message") - error_id=$(echo $create_storage_response | jq -r ".errorIdentifier") + error_message=$(echo $op_storage_create_response | jq -r ".message") + error_id=$(echo $op_storage_create_response | jq -r ".errorIdentifier") if [[ ${error_id} == "urn:openproject-org:api:v3:errors:MultipleErrors" ]]; then # If the files storage is already created with the provided Nextcloud host and storage name. # We assume that the integration setup is already done in both applications. # To check that, we parse the error messages. # If there are only two error messages and those are about the Nextcloud host and name being taken. # We assume the setup was already completed. - error_messages_grep=$(echo $create_storage_response | jq -r '.["_embedded"]["errors"] | .[].message') + error_messages_grep=$(echo $op_storage_create_response | jq -r '.["_embedded"]["errors"] | .[].message') readarray -t error_messages <<<"$error_messages_grep" error_count=0 host_already_taken=false @@ -444,7 +533,7 @@ if [[ ${response_type} == "Error" ]]; then logAlreadyCompletedIntegrationConfiguration elif [[ ${error_id} == "urn:openproject-org:api:v3:errors:PropertyConstraintViolation" ]]; then # A PropertyConstraintViolation is always a single error - error_messages_grep=$(echo $create_storage_response | jq -r '.message') + error_messages_grep=$(echo $op_storage_create_response | jq -r '.message') if [[ "$error_messages_grep" == "Host has already been taken." || "$error_messages_grep" == "Name has already been taken." ]]; then opCheckIntegrationConfiguration ncCheckIntegrationConfiguration @@ -464,10 +553,10 @@ if [[ ${response_type} == "Error" ]]; then fi # Required information from the above response -OP_STORAGE_ID=$(echo $create_storage_response | jq -e '.id') +OP_STORAGE_ID=$(echo $op_storage_create_response | jq -e '.id') if [[ ${OP_STORAGE_ID} == null ]]; then - echo "${create_storage_response}" | jq + echo "${op_storage_create_response}" | jq log_error "Response does not contain $OP_STORAGE_ID (id)." log_error "Setup of OpenProject and Nextcloud integration failed." exit 1 @@ -499,7 +588,7 @@ cat >${INTEGRATION_SETUP_TEMP_DIR}/request_body_4_nc_integration_setup.json <