diff --git a/client/defines.h b/client/defines.h
index c112074..637eb31 100644
--- a/client/defines.h
+++ b/client/defines.h
@@ -199,4 +199,5 @@ typedef enum
     {ERROR_TDNF_RPM_CHECK,           "ERROR_TDNF_RPM_CHECK",           "rpm check reported errors"}, \
     {ERROR_TDNF_METADATA_EXPIRE_PARSE, "ERROR_TDNF_METADATA_EXPIRE_PARSE", "metadata_expire value could not be parsed. Check your repo files."},\
     {ERROR_TDNF_SELF_ERASE, "ERROR_TDNF_SELF_ERASE", "The operation would result in removing the protected package : tdnf"},\
+    {ERROR_TDNF_PERM, "ERROR_TDNF_PERM", "Operation not permitted. You have to be root."},\
 };
diff --git a/client/packageutils.c b/client/packageutils.c
index 6b86d20..0ee3212 100644
--- a/client/packageutils.c
+++ b/client/packageutils.c
@@ -763,22 +763,14 @@ TDNFPopulatePkgInfos(
                       (void**)&pPkgInfo);
         BAIL_ON_TDNF_ERROR(dwError);
 
-        dwError = SolvGetPkgNameFromId(pSack, dwPkgId, &pPkgInfo->pszName);
-        BAIL_ON_TDNF_ERROR(dwError);
-
-        dwError = SolvGetPkgVersionFromId(
-                      pSack,
-                      dwPkgId,
-                      &pPkgInfo->pszVersion);
-        BAIL_ON_TDNF_ERROR(dwError);
-
-        dwError = SolvGetPkgReleaseFromId(
+        dwError = SolvGetNevraFromId(
                       pSack,
                       dwPkgId,
-                      &pPkgInfo->pszRelease);
-        BAIL_ON_TDNF_ERROR(dwError);
-
-        dwError = SolvGetPkgArchFromId(pSack, dwPkgId, &pPkgInfo->pszArch);
+                      &pPkgInfo->dwEpoch,
+                      &pPkgInfo->pszName,
+                      &pPkgInfo->pszVersion,
+                      &pPkgInfo->pszRelease,
+                      &pPkgInfo->pszArch);
         BAIL_ON_TDNF_ERROR(dwError);
 
         dwError = SolvGetPkgRepoNameFromId(
diff --git a/client/rpmtrans.c b/client/rpmtrans.c
index 212169d..92e88bf 100644
--- a/client/rpmtrans.c
+++ b/client/rpmtrans.c
@@ -29,14 +29,15 @@ TDNFRpmExecTransaction(
 {
     uint32_t dwError = 0;
     int nKeepCachedRpms = 0;
-    TDNFRPMTS ts = {pTdnf->pArgs->nQuiet};
+    TDNFRPMTS ts = {0};
 
-    if(!pTdnf || !pTdnf->pConf || !pSolvedInfo)
+    if(!pTdnf || !pTdnf->pArgs || !pTdnf->pConf || !pSolvedInfo)
     {
         dwError = ERROR_TDNF_INVALID_PARAMETER;
         BAIL_ON_TDNF_ERROR(dwError);
     }
 
+    ts.nQuiet = pTdnf->pArgs->nQuiet;
     nKeepCachedRpms = pTdnf->pConf->nKeepCache;
 
     dwError = TDNFAllocateMemory(
diff --git a/include/tdnferror.h b/include/tdnferror.h
index 9033efc..1eeb714 100644
--- a/include/tdnferror.h
+++ b/include/tdnferror.h
@@ -122,10 +122,11 @@ extern "C" {
 #define ERROR_TDNF_TRANS_INCOMPLETE     1525
 #define ERROR_TDNF_TRANS_PKG_NOT_FOUND  1526
 
-//System errors 1600 and up
-#define ERROR_TDNF_SYSTEM_BASE          1600
 // No search results found
-#define ERROR_TDNF_NO_SEARCH_RESULTS    1601
+#define ERROR_TDNF_NO_SEARCH_RESULTS    1599
+#define ERROR_TDNF_SYSTEM_BASE          1600
+//System errors 1600 and up
+#define ERROR_TDNF_PERM                 (ERROR_TDNF_SYSTEM_BASE + EPERM)
 #define ERROR_TDNF_INVALID_PARAMETER    (ERROR_TDNF_SYSTEM_BASE + EINVAL)
 #define ERROR_TDNF_OUT_OF_MEMORY        (ERROR_TDNF_SYSTEM_BASE + ENOMEM)
 #define ERROR_TDNF_NO_DATA              (ERROR_TDNF_SYSTEM_BASE + ENODATA)
diff --git a/include/tdnftypes.h b/include/tdnftypes.h
index f2fbdb5..d89163c 100644
--- a/include/tdnftypes.h
+++ b/include/tdnftypes.h
@@ -160,6 +160,7 @@ typedef struct _TDNF_SOLVED_PKG_INFO
 {
     int nNeedAction;
     int nNeedDownload;
+    TDNF_ALTERTYPE nAlterType;
     PTDNF_PKG_INFO pPkgsNotAvailable;
     PTDNF_PKG_INFO pPkgsExisting;
     PTDNF_PKG_INFO pPkgsToInstall;
diff --git a/solv/prototypes.h b/solv/prototypes.h
index 2484649..9789316 100644
--- a/solv/prototypes.h
+++ b/solv/prototypes.h
@@ -246,6 +246,17 @@ SolvFindHighestOrLowestInstalled(
     uint32_t dwFindHighest
     );
 
+uint32_t
+SolvGetNevraFromId(
+    PSolvSack pSack,
+    uint32_t dwPkgId,
+    uint32_t *pdwEpoch,
+    char **ppszName,
+    char **ppszVersion,
+    char **ppszRelease,
+    char **ppszArch
+    );
+
 // tdnfpool.c
 uint32_t
 SolvCreateSack(
diff --git a/solv/tdnfpackage.c b/solv/tdnfpackage.c
index 9631cde..80c33c2 100644
--- a/solv/tdnfpackage.c
+++ b/solv/tdnfpackage.c
@@ -1673,3 +1673,118 @@ SolvIsGlob(
     }
     return nResult;
 }
+
+uint32_t
+SolvGetNevraFromId(
+    PSolvSack pSack,
+    uint32_t dwPkgId,
+    uint32_t *pdwEpoch,
+    char **ppszName,
+    char **ppszVersion,
+    char **ppszRelease,
+    char **ppszArch
+    )
+{
+    uint32_t dwError = 0;
+    const char* pszTmp = NULL;
+    Solvable *pSolv = NULL;
+    uint32_t dwEpoch = 0;
+    char *pszName = NULL;
+    char *pszEpoch = NULL;
+    char *pszVersion = NULL;
+    char *pszRelease = NULL;
+    char *pszArch = NULL;
+
+    if(!pSack ||
+       !ppszName ||
+       !ppszVersion ||
+       !ppszRelease ||
+       !ppszArch ||
+       !pdwEpoch)
+    {
+        dwError = ERROR_TDNF_INVALID_PARAMETER;
+        BAIL_ON_TDNF_LIBSOLV_ERROR(dwError);
+    }
+
+    pSolv = pool_id2solvable(pSack->pPool, dwPkgId);
+    if(!pSolv)
+    {
+        dwError = ERROR_TDNF_NO_DATA;
+        BAIL_ON_TDNF_ERROR(dwError);
+    }
+
+    pszTmp = solvable_lookup_str(pSolv, SOLVABLE_NAME);
+    if(!pszTmp)
+    {
+        dwError = ERROR_TDNF_NO_DATA;
+        BAIL_ON_TDNF_ERROR(dwError);
+    }
+
+    dwError = TDNFAllocateString(pszTmp, &pszName);
+    BAIL_ON_TDNF_ERROR(dwError);
+
+    pszTmp = solvable_lookup_str(pSolv, SOLVABLE_ARCH);
+    if(!pszTmp)
+    {
+        dwError = ERROR_TDNF_NO_DATA;
+        BAIL_ON_TDNF_ERROR(dwError);
+    }
+
+    dwError = TDNFAllocateString(pszTmp, &pszArch);
+    BAIL_ON_TDNF_ERROR(dwError);
+
+    pszTmp = solvable_lookup_str(pSolv, SOLVABLE_EVR);
+    if(!pszTmp)
+    {
+        dwError = ERROR_TDNF_NO_DATA;
+        BAIL_ON_TDNF_ERROR(dwError);
+    }
+
+    dwError = SolvSplitEvr(pSack,
+                           pszTmp,
+                           &pszEpoch,
+                           &pszVersion,
+                           &pszRelease);
+    BAIL_ON_TDNF_ERROR(dwError);
+
+    if(!IsNullOrEmptyString(pszEpoch))
+    {
+        dwEpoch = strtol(pszEpoch, NULL, 10);
+    }
+
+    *pdwEpoch = dwEpoch;
+    *ppszName = pszName;
+    *ppszVersion = pszVersion;
+    *ppszRelease = pszRelease;
+    *ppszArch = pszArch;
+cleanup:
+    TDNF_SAFE_FREE_MEMORY(pszEpoch);
+    return dwError;
+
+error:
+    if(pdwEpoch)
+    {
+        *pdwEpoch = 0;
+    }
+    if(ppszName)
+    {
+        *ppszName = NULL;
+    }
+    if(ppszVersion)
+    {
+        *ppszVersion = NULL;
+    }
+    if(ppszRelease)
+    {
+        *ppszRelease = NULL;
+    }
+    if(ppszArch)
+    {
+        *ppszArch = NULL;
+    }
+    TDNF_SAFE_FREE_MEMORY(pszName);
+    TDNF_SAFE_FREE_MEMORY(pszVersion);
+    TDNF_SAFE_FREE_MEMORY(pszRelease);
+    TDNF_SAFE_FREE_MEMORY(pszArch);
+    goto cleanup;
+}
diff --git a/tools/cli/main.c b/tools/cli/main.c
index c1df143..dc7a505 100644
--- a/tools/cli/main.c
+++ b/tools/cli/main.c
@@ -63,6 +63,15 @@ int main(int argc, char* argv[])
     PTDNF pTdnf = NULL;
     int nFound = 0;
 
+    //granular permissions for non root users are pending.
+    //blocking all operations for non root and show the
+    //right error to avoid confusion.
+    if(geteuid() != 0)
+    {
+        dwError = ERROR_TDNF_PERM;
+        BAIL_ON_CLI_ERROR(dwError);
+    }
+
     _context.pFnCheck = TDNFCliInvokeCheck;
     _context.pFnCheckLocal = TDNFCliInvokeCheckLocal;
     _context.pFnCheckUpdate = TDNFCliInvokeCheckUpdate;