{
  "date": "2017-03-10T10:37:01",
  "slug": "12cr2-tns_admin-in-env-ora",
  "link": "https://www.dbi-services.com/blog/12cr2-tns_admin-in-env-ora/",
  "title": {
    "rendered": "12cR2: TNS_ADMIN in env.ora"
  },
  "content": {
    "rendered": "<h2>By Franck Pachot</h2>\n<p>.<br />\nThe network files (sqlnet.ora, tnsnames.ora, lsnrctl.ora) are read by default from ORACLE_HOME/network/admin but you may have several Oracle installations, and want only one place for those files. Then you can use TNS_ADMIN environment variable. But are you sure that it is always set when starting the database? the listener? the client? They must be consistent (see <a href=\"https://www.dbi-services.com/blog/oracle-12cr2-plsql-new-feature-tnsping-from-the-database/\">https://www.dbi-services.com/blog/oracle-12cr2-plsql-new-feature-tnsping-from-the-database/</a>). Then what we do for the cases where TNS_ADMIN is not set: define symbolic links from the ORACLE_HOME to the common location. It would be better to just change the default location and this is what can be done in 12.2 with env.ora<br />\n<!--more--><br />\nBy default, the $ORACLE_HOME/env.ora is empty. There are only comments.</p>\n<p>If you run any oracle 12.2 client the $ORACLE_HOME/ora.env will be read. If nothing is set here, then the default $ORACLE_HOME/network/admin location is read.</p>\n<h3>$ORACLE_HOME/network/admin</h3>\n<pre><code>[oracle@VM104 tmp]$ strace -e trace=file tnsping localhost 2&gt;&amp;1 | grep -E \"[.]ora\"\nlstat(\"/u01/app/oracle/product/12.2.0/dbhome_1/env.ora\", {st_mode=S_IFREG|0644, st_size=852, ...}) = 0\nopen(\"/u01/app/oracle/product/12.2.0/dbhome_1/env.ora\", O_RDONLY) = 3\naccess(\"/u01/app/oracle/product/12.2.0/dbhome_1/network/admin/sqlnet.ora\", F_OK) = 0\nopen(\"/u01/app/oracle/product/12.2.0/dbhome_1/network/admin/sqlnet.ora\", O_RDONLY) = 3\naccess(\"/u01/app/oracle/product/12.2.0/dbhome_1/network/admin/sqlnet.ora\", F_OK) = 0\nopen(\"/u01/app/oracle/product/12.2.0/dbhome_1/network/admin/sqlnet.ora\", O_RDONLY) = 3\naccess(\"/home/oracle/.tnsnames.ora\", F_OK) = -1 ENOENT (No such file or directory)\naccess(\"/etc/tnsnames.ora\", F_OK)       = -1 ENOENT (No such file or directory)\naccess(\"/u01/app/oracle/product/12.2.0/dbhome_1/network/admin/tnsnames.ora\", F_OK) = -1 ENOENT (No such file or directory)\n</code></pre>\n<p>Here I have a sqlnet.ora but no tnsnames.ora so the next locations that are searched are ~/.tnsnames.ora and /etc/tnsnames.ora</p>\n<h3>TNS_ADMIN environment variable</h3>\n<p>If I set the environment variable TNS_ADMIN to /tmp then </p>\n<pre><code>[oracle@VM104 tmp]$ TNS_ADMIN=/tmp strace -e trace=file tnsping localhost 2&gt;&amp;1 | grep -E \"[.]ora\"\nlstat(\"/u01/app/oracle/product/12.2.0/dbhome_1/env.ora\", {st_mode=S_IFREG|0644, st_size=852, ...}) = 0\nopen(\"/u01/app/oracle/product/12.2.0/dbhome_1/env.ora\", O_RDONLY) = 3\naccess(\"/tmp/sqlnet.ora\", F_OK)         = 0\nopen(\"/tmp/sqlnet.ora\", O_RDONLY)       = 3\naccess(\"/tmp/sqlnet.ora\", F_OK)         = 0\nopen(\"/tmp/sqlnet.ora\", O_RDONLY)       = 3\naccess(\"/home/oracle/.tnsnames.ora\", F_OK) = -1 ENOENT (No such file or directory)\naccess(\"/tmp/tnsnames.ora\", F_OK)       = -1 ENOENT (No such file or directory)\naccess(\"/etc/tnsnames.ora\", F_OK)       = -1 ENOENT (No such file or directory)\naccess(\"/u01/app/oracle/product/12.2.0/dbhome_1/network/admin/tnsnames.ora\", F_OK) = -1 ENOENT (No such file or directory)\n</code></pre>\n<p>The directory defined in TNS_ADMIN is searched first</p>\n<h3>TNS_ADMIN in env.ora</h3>\n<p>I have added the TNS_ADMIN=/tmp in the env.ora:</p>\n<pre><code>[oracle@VM104 tmp]$ tail -3 $ORACLE_HOME/env.ora\n#   Default: $ORACLE_HOME/network/admin\n#\nTNS_ADMIN=/tmp\n</code></pre>\n<p>When I run tnsping without setting any environment variable, I have exactly the same as before:</p>\n<pre><code>\n[oracle@VM104 tmp]$ strace -e trace=file tnsping localhost 2&gt;&amp;1 | grep -E \"[.]ora\"\nlstat(\"/u01/app/oracle/product/12.2.0/dbhome_1/env.ora\", {st_mode=S_IFREG|0644, st_size=867, ...}) = 0\nopen(\"/u01/app/oracle/product/12.2.0/dbhome_1/env.ora\", O_RDONLY) = 3\naccess(\"/tmp/sqlnet.ora\", F_OK)         = 0\nopen(\"/tmp/sqlnet.ora\", O_RDONLY)       = 3\naccess(\"/tmp/sqlnet.ora\", F_OK)         = 0\nopen(\"/tmp/sqlnet.ora\", O_RDONLY)       = 3\naccess(\"/home/oracle/.tnsnames.ora\", F_OK) = -1 ENOENT (No such file or directory)\naccess(\"/tmp/tnsnames.ora\", F_OK)       = -1 ENOENT (No such file or directory)\naccess(\"/etc/tnsnames.ora\", F_OK)       = -1 ENOENT (No such file or directory)\naccess(\"/u01/app/oracle/product/12.2.0/dbhome_1/network/admin/tnsnames.ora\", F_OK) = -1 ENOENT (No such file or directory)\n</code></pre>\n<p>The good thing about it is that the setting is centralized for all binaries running from this ORACLE_HOME set.</p>\n<h3>Both</h3>\n<p>However the setting in environment has priority over the env.ora one:</p>\n<pre><code>[oracle@VM104 tmp]$ TNS_ADMIN=/var/tmp strace -e trace=file tnsping localhost 2&gt;&amp;1 | grep -E \"[.]ora\"\nlstat(\"/u01/app/oracle/product/12.2.0/dbhome_1/env.ora\", {st_mode=S_IFREG|0644, st_size=867, ...}) = 0\nopen(\"/u01/app/oracle/product/12.2.0/dbhome_1/env.ora\", O_RDONLY) = 3\naccess(\"/var/tmp/sqlnet.ora\", F_OK)     = 0\nopen(\"/var/tmp/sqlnet.ora\", O_RDONLY)   = 3\naccess(\"/var/tmp/sqlnet.ora\", F_OK)     = 0\nopen(\"/var/tmp/sqlnet.ora\", O_RDONLY)   = 3\naccess(\"/home/oracle/.tnsnames.ora\", F_OK) = -1 ENOENT (No such file or directory)\naccess(\"/var/tmp/tnsnames.ora\", F_OK)   = -1 ENOENT (No such file or directory)\naccess(\"/etc/tnsnames.ora\", F_OK)       = -1 ENOENT (No such file or directory)\naccess(\"/u01/app/oracle/product/12.2.0/dbhome_1/network/admin/tnsnames.ora\", F_OK) = -1 ENOENT (No such file or directory)</code></pre>\n<p>So the recommandation if you want to use the env.ora is not to set TNS_ADMIN, especially when starting the listener or the database, to be sure that the same environment is always used. Final note: I&#8217;ve not seen it in the documentation so if you rely on it for critical environment, better to validate with support.</p>\n",
    "protected": false
  }
}
