decide( * $comment_text, * array( 'spam' => DecisionQuestion::noul( 'Is this comment spam?' ) ) * ); * * @since 1.3.0 * * @param string $model_id The model ID, such as "nimble". * @param \WordPress\AiClient\Providers\Models\DTO\ModelConfig|null $model_config Optional. Model configuration, * for custom options. Default null. * @return \Fueled\AiProviderForOllama\Models\OllamaDecisionModel The decision model. */ public static function decisionModel( string $model_id, ?ModelConfig $model_config = null ): OllamaDecisionModel { $model_metadata = new ModelMetadata( $model_id, $model_id, array(), array( new SupportedOption( OptionEnum::customOptions() ) ) ); $model = new OllamaDecisionModel( $model_metadata, static::metadata() ); if ( null !== $model_config ) { $model->setConfig( $model_config ); } $registry = AiClient::defaultRegistry(); if ( $registry->hasProvider( static::class ) ) { $registry->bindModelDependencies( $model ); } return $model; } /** * Lists the models on the Ollama host that support decisions. * * @since 1.3.0 * * @return list The model IDs, sorted. * @throws \WordPress\AiClient\Providers\Http\Exception\ResponseException If the host is unreachable. */ public static function decisionModelIds(): array { /** @var \Fueled\AiProviderForOllama\Metadata\OllamaModelMetadataDirectory $model_metadata_directory */ $model_metadata_directory = static::modelMetadataDirectory(); return $model_metadata_directory->listDecisionModelIds(); } /** * {@inheritDoc} * * @since 1.0.0 */ protected static function baseUrl(): string { $host = getenv( 'OLLAMA_HOST' ); if ( false !== $host && '' !== $host ) { return rtrim( $host, '/' ); } return 'http://localhost:11434'; } /** * {@inheritDoc} * * @since 1.0.0 */ protected static function createModel( ModelMetadata $model_metadata, ProviderMetadata $provider_metadata ): ModelInterface { $capabilities_string_list = $model_metadata->toArray()[ ModelMetadata::KEY_SUPPORTED_CAPABILITIES ]; if ( in_array( 'image_generation', $capabilities_string_list, true ) ) { return new OllamaImageGenerationModel( $model_metadata, $provider_metadata ); } $capabilities = $model_metadata->getSupportedCapabilities(); foreach ( $capabilities as $capability ) { if ( $capability->isTextGeneration() ) { return new OllamaTextGenerationModel( $model_metadata, $provider_metadata ); } // The embedding contracts are unreleased in some SDK versions; the model class cannot load there. if ( $capability->isEmbeddingGeneration() && interface_exists( EmbeddingGenerationModelInterface::class ) ) { return new OllamaEmbeddingGenerationModel( $model_metadata, $provider_metadata ); } if ( $capability->isTextToSpeechConversion() ) { return new OllamaTextToSpeechConversionModel( $model_metadata, $provider_metadata ); } } throw new RuntimeException( // phpcs:ignore WordPress.Security.EscapeOutput.ExceptionNotEscaped -- Exception message, not output. 'Unsupported model capabilities: ' . implode( ', ', $capabilities ) ); } /** * {@inheritDoc} * * @since 1.0.0 */ protected static function createProviderMetadata(): ProviderMetadata { $provider_meta = array( 'ollama', 'Ollama', ProviderTypeEnum::cloud(), 'https://ollama.com/settings/keys', RequestAuthenticationMethod::apiKey(), ); // Provider description support was added in 1.2.0. if ( version_compare( AiClient::VERSION, '1.2.0', '>=' ) ) { if ( function_exists( '__' ) ) { $provider_meta[] = __( 'Text, image, embedding, and speech generation with Ollama, either running locally or on Ollama Cloud.', 'ai-provider-for-ollama' ); } else { $provider_meta[] = 'Text, image, embedding, and speech generation with Ollama, either running locally or on Ollama Cloud.'; } } // Provider logo path support was added in 1.3.0. if ( version_compare( AiClient::VERSION, '1.3.0', '>=' ) ) { $provider_meta[] = defined( 'AI_PROVIDER_FOR_OLLAMA_PLUGIN_DIR' ) ? AI_PROVIDER_FOR_OLLAMA_PLUGIN_DIR . 'includes/Provider/logo.svg' : dirname( __DIR__, 2 ) . '/includes/Provider/logo.svg'; } return new ProviderMetadata( ...$provider_meta ); } /** * {@inheritDoc} * * @since 1.0.0 */ protected static function createProviderAvailability(): ProviderAvailabilityInterface { /** @var \Fueled\AiProviderForOllama\Metadata\OllamaModelMetadataDirectory $model_metadata_directory */ $model_metadata_directory = static::modelMetadataDirectory(); // Check valid API access by fetching the model tags, the cheapest complete answer Ollama gives. return new OllamaProviderAvailability( $model_metadata_directory ); } /** * {@inheritDoc} * * @since 1.0.0 */ protected static function createModelMetadataDirectory(): ModelMetadataDirectoryInterface { return new OllamaModelMetadataDirectory(); } }