diff --git a/CHANGELOG.md b/CHANGELOG.md
index 9f0fcd58b885..d19fe6ae6083 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -200,6 +200,7 @@ Inspired from [Keep a Changelog](https://keepachangelog.com/en/1.0.0/)
 - Add path ignore for markdown files for CI ([#2312](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/2312))
 - Updating WS scans to ignore BWC artifacts in `cypress` ([#2408](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/2408))
 - [CI] Run functional test repo as workflow ([#2503](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/2503))
+- Add downgrade logic for branch in DocLinkService([#3483](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3483))
 
 ### 📝 Documentation
 
diff --git a/src/core/public/doc_links/doc_links_service.test.ts b/src/core/public/doc_links/doc_links_service.test.ts
index 0ba91c21ccc3..1c1dfc75ace6 100644
--- a/src/core/public/doc_links/doc_links_service.test.ts
+++ b/src/core/public/doc_links/doc_links_service.test.ts
@@ -64,4 +64,16 @@ describe('DocLinksService#start()', () => {
       'https://opensearch.org/docs/1.1/dashboards/index/'
     );
   });
+
+  it('templates the doc links with the build version from injectedMetadata', () => {
+    const injectedMetadata = injectedMetadataServiceMock.createStartContract();
+    injectedMetadata.getOpenSearchDashboardsBranch.mockReturnValue('test-branch');
+    injectedMetadata.getOpenSearchDashboardsVersion.mockReturnValue('1.1.2');
+    const service = new DocLinksService();
+    const api = service.start({ injectedMetadata });
+    expect(api.DOC_LINK_VERSION).toEqual('1.1');
+    expect(api.links.opensearchDashboards.introduction).toEqual(
+      'https://opensearch.org/docs/1.1/dashboards/index/'
+    );
+  });
 });
diff --git a/src/core/public/doc_links/doc_links_service.ts b/src/core/public/doc_links/doc_links_service.ts
index 109e3d9c1773..1d621550e4be 100644
--- a/src/core/public/doc_links/doc_links_service.ts
+++ b/src/core/public/doc_links/doc_links_service.ts
@@ -29,6 +29,7 @@
  */
 
 import { deepFreeze } from '@osd/std';
+import { parse } from 'semver';
 import { InjectedMetadataSetup } from '../injected_metadata';
 
 interface StartDeps {
@@ -39,10 +40,24 @@ interface StartDeps {
 export class DocLinksService {
   public setup() {}
   public start({ injectedMetadata }: StartDeps): DocLinksStart {
-    const DOC_LINK_VERSION =
-      injectedMetadata.getOpenSearchDashboardsBranch() === 'main'
-        ? 'latest'
-        : injectedMetadata.getOpenSearchDashboardsBranch();
+    const buildVersion = injectedMetadata.getOpenSearchDashboardsVersion();
+    const pkgBranch = injectedMetadata.getOpenSearchDashboardsBranch();
+    /**
+     * OpenSearch server uses the `branch` property from `package.json` to
+     * build links to the documentation. If set to `main`, it would use `/latest`
+     * and if not, it would use the `version` to construct URLs.
+     */
+    let branch = pkgBranch;
+    if (pkgBranch === 'main') {
+      branch = 'latest';
+    } else {
+      const validDocPathsPattern = /^\d+\.\d+$/;
+      const parsedBuildVersion = parse(buildVersion);
+      if (!validDocPathsPattern.test(pkgBranch) && parsedBuildVersion) {
+        branch = `${parsedBuildVersion.major}.${parsedBuildVersion.minor}`;
+      }
+    }
+    const DOC_LINK_VERSION = branch;
     const OPENSEARCH_WEBSITE_URL = 'https://opensearch.org/';
     const OPENSEARCH_WEBSITE_DOCS = `${OPENSEARCH_WEBSITE_URL}docs/${DOC_LINK_VERSION}`;
     const OPENSEARCH_VERSIONED_DOCS = `${OPENSEARCH_WEBSITE_DOCS}/opensearch/`;