License file LICX Issues

Hi guys,

First the background story. We develop everything in nugets on the .net side of things. If someone wants to talk to a service you go and download the nuget that offers the require api/stuff to connect to it and done. These applies to all interacting dev teams.

For RO I built some custom nuggets where I embedded the required dlls, plus the generated intf file, some extra client side logic and good to go. This was fine until I wanted clients to call DA methods, not just RO services.

Suddenly it now complaints about licenses. Just to make it even better our nugets are .net standard.

So I read the forum and saw multiple options also saw issues with nugets and licx files etc, etc multiple workarounds but nothing in concrete and I’m failing on something as simple as just deploying a workable client side app.

So, first how do I have a CLIENT app/service/program connecting to a DA server on my case scenario. I dont control other development teams, they just grab their nuget, add connection strings and good to go. I can not ask them to include a separate class and a file with embedded resources, that gets into each team realm and cant get there.

Server side is fine, I control that, client side other teams do it.

I remembered there was a big division on client and server side components just to skip these kind of situations, I’m wondering why do we even need a client side license.

I’m probably just doing things wrong cause I dont see a reason to do it on connecting apps if license is the concern.

Any assistance is extremely welcome, I developed this big thing, relying on DA and now suddenly I cant deploy it for others to use because they are complaining with the license errors. Obviously I ended discovering this up to the moment of integration with other services way to deep into development to find an alternative working solution instead of DA.

Thank you in advance.

Hello

licensing.licx is one of the things in the list to review (we have been discussing it literally yesterday).

Still you cannot wait for any changes in this area so let’s resolve the issue with the current license restrictions.

If your DA-based NuGet package contains additional assembly (assemblies) with your code (like API definitions, table definitions and so on) and other teams are expected to work with DA servers via these APIs then you can just add the licenses.licx file to that assembly project with contents like

RemObjects.DataAbstract.RemoteDataAdapter, RemObjects.DataAbstract
RemObjects.DataAbstract.Linq.LinqRemoteDataAdapter, RemObjects.DataAbstract
RemObjects.DataAbstract.RemoteCommand, RemObjects.DataAbstract

Once referenced the assembly will provide the required licensing info.
Teams won’t have to do any client code changes or reference any additional stuff (like resource files).

Note: In some cases (like republishing a nuget package with the same version) you might need to clear the NuGet caches to ensure that new package is fetched from the source.

Hi,

Ok, so this is what I did. I added to my class library that has extra definitions, the _intf generated files and a nugget with DA/RO dlls a file called “Licenses.licx”

The file contains the lines you described above. The file Build Action is set to None and the Copy Output Directory is set to Do not copy.

This library is actually converted into a nuget package which holds a dependency to the RO/DA nuget so when it is installed it will bring the RO/DA dlls with it.

If I create a console app and I add the mentioned nuget everything comes with it and usually it will work until I added the DA calls.

What exactly do I need to do? step by step will be great, cause I’m on desperate mode and I’ve being trying all sort of experiments for now.

Just for the record, this is the exception message (btw, as part of the experiments I also added the type described below on the file with no difference):

System.ComponentModel.LicenseException: No valid license has been found for the type RemObjects.DataAbstract.BaseDataAdapter
at RemObjects.DataAbstract.ROLicenseProvider.GetLicense(LicenseContext context, Type licenseType, Object licenseInstance, Boolean allowExceptions)
at System.ComponentModel.LicenseManager.ValidateInternalRecursive(LicenseContext context, Type type, Object instance, Boolean allowExceptions, License& license, String& licenseKey)
at System.ComponentModel.LicenseManager.ValidateInternal(Type type, Object instance, Boolean allowExceptions, License& license)
at System.ComponentModel.LicenseManager.Validate(Type type, Object instance)
at RemObjects.DataAbstract.BaseDataAdapter…ctor(Boolean avoidLicenseCheck)
at RemObjects.DataAbstract.BaseDataAdapter…ctor()
at RemObjects.DataAbstract.DataAdapter…ctor()
at RemObjects.DataAbstract.RemoteDataAdapter…ctor()
at ConsoleApp1.Program.Main(String[] args) in XXXX

Thank you.

Hello

Please do the following:

  1. Fast sanity check. Please open your compiled class library (the one you put into nuget) with something like dotPeek and make sure that there is a compiled licenses resource (its extension should be .licenses). You might need to set the licenses.licx Build Action to Embedded Resource instead of None
  2. Clear your nuget cache before trying to use the new nuget
  3. Before creating RemoteAdapter in your test case app somehow access any type from the class lib containing licenses. Even a simple typeof(class from class lib) should be enough. The reason for this step is to ensure they .net actually loads the assembly containing licenses. Just referencing an assembly won’t result in .net loading into an app domain due to the lazy approach to reference loading used in .net
  4. If the above helps (it should) then add an empty class named like LicenseManager to your class lib with some empty method and require other themes to call this method once during their app startup or before instantiating data adapters. This step is required only if they are expected to create remote data adapters directly. If they will work via classes defined in the class lib then it will be loaded anyway before the license check occurs and there will she no need to make additional classes.

I can confirm that the abovementioned approach works.

Two things that should be kept in mind are:

  1. licenses.licx Build Action should be set to Embedded Resource
  2. You need to ensure that the license carrier assembly is loaded into memory before any DataAdapter is instantiated for the first time.

F.e. in the exception above you directly create RemoteDataAdapter instance. This means that even if the nuget with custom code is referenced, it is not guaranteed that its assemblies are already loaded into the process. This means that the license cannot be located (because it is not present in the AppDomain at the moment when the check is performed)

Attached is a simple class library project that puts licenses info into NuGet: ClassLibrary_NG_Test.zip (2.2 KB)
There’s literally no code except this class:

using System;

namespace ClassLibrary_NG_Test
{
	public static class LicenseManager
	{
		public static void Init()
		{
		}
	}
}

Its consumer code (that I used as a testcase) is

using System;
using RemObjects.DataAbstract.Linq;

namespace ConsoleApp9
{
	class Program
	{
		static void Main(string[] args)
		{
			try
			{
				ClassLibrary_NG_Test.LicenseManager.Init();
				var da = new LinqRemoteDataAdapter();
				Console.WriteLine("Done");
			}
			catch (Exception e)
			{
				Console.WriteLine(e.ToString());
			}
		}
	}
}

Note the line

ClassLibrary_NG_Test.LicenseManager.Init()

This call (despite it actually does nothing) ensures that assembly from the ClassLibrary_NG_Test nuget is loaded into the application. Then the LinqRemoteDataAdapter is instantiated without any issues using the license provided via the ClassLibrary_NG_Test package.
Commenting out this line will result in the same exception you had

The project: ConsoleApp9.zip (1.5 KB)

Please note that you will need to update DataAbstract package references to the ones you created in the case you will want to use this code in action.

Hi Anton,

I haven’t had the chance to reply to thank you because I was busy updating everything once I made it work. Thank you very much, it works.

These changes will do while the license stuff gets resolved.

Once again, thank you.