SSRS 2016 Report - Populate table from string parameter - string

Let's assume I have the following C# object:
public class BusinessDetails
{
public string Name { get; set; }
public string Address1 { get; set; }
public string Address2 { get; set; }
}
Long story short my solution [A] sends a serialised (JSON) List<BusinessDetails> to another external solution [B] that in turn feeds the RDL in question with this and other provided parameters (strings); therefore, on the RDL level I am limited to strings and strings only.
This is all good for simple, one value string parameters but I am interested in dynamically populating table from (JSON 'flattened'/string) List<BusinessDetails> in the mentioned RDL.
I see the available parameter types are:
Text
Boolean
Date/Time
Integer
Float
I guess my question is - can I use the Text/string param to dynamically populate a table in RDL?
Thanks.

short anser NO!
long answer: you dont need that, using the report viewer control you can use the list directly as datasource, when using rdlc instead of rdl you can even consume the class in the reportdesigner, you dont have to come up with ways to align your data source mapping with the data you are recieving
read this for further info: Creating a PDF from a RDLC Report in the Background

Related

EF Core 7 t4 file - get string length

I've installed the default t4 templates for EF Core into my project, and now I want to edit the EntityType.t4 template so that for any varchar field, I generate a static variable with the max length. For example, the scaffold right now will generate a line like:
public string? CollateralName { get; set; }
When it does that, I also want it to add:
public const int CollateralNamePropertyMaxLength = 50;
I can see in the t4 file where it's writing the property, but I'm not sure how to get the max length of the string from the database column.

How to force Azure Storage Table to save DateTime in specified format

I am saving a DateTime value into Azure Table Storage. The DateTime is being parsed from unix milliseconds format like so:
DateTimeOffset.FromUnixTimeMilliseconds(milliseconds).UtcDateTime;
When I look into the table via storage explorer the DateTimes have variable length.
See Image
I was trying find out how to force the table to store the date in the following format but I wasn't able to find a way:
"yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'fff'Z'"
Is there a way to force the desired format? Thanks
I was trying find out how to force the table to store the date in the
following format but I wasn't able to find a way: "yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'fff'Z'" Is there a way to force the desired format? Thanks
This is not possible to force on Azure Table Storage. You can apply this type of logic on application code level.
Like application level you can set.
internal class Program
{
static string storageconn = "DefaultEndpointsProtocol=https;AccountName=storageaccount87819573y6;AccountKey=xxxxx;EndpointSuffix=core.windows.net";
static string table = "Datetimetable";
static string partitionkey = "Debasis Saha";
static string rowKey = "userC";
static void Main(string[] args)
{
Microsoft.Azure.Cosmos.Table.CloudStorageAccount storageAcc = Microsoft.Azure.Cosmos.Table.CloudStorageAccount.Parse(storageconn);
Microsoft.Azure.Cosmos.Table.CloudTableClient tblclient = storageAcc.CreateCloudTableClient(new TableClientConfiguration());
Microsoft.Azure.Cosmos.Table.CloudTable table1 = tblclient.GetTableReference(table);
Console.ReadKey();
string datetime = DateTime.UtcNow.ToString("yyyy-MM-dd HH:mm:ss.fff");
Console.WriteLine(datetime);
Console.ReadKey();
}
Output :- you can pass this datetime to Azure Table Storage.

PXDBCreatedDateTime doesn't work in Extension Table

I have a User Defined Table that I link to the BAccount table in Acumatica. What I'm trying to do is use the PXDBCreatedDateTime attribute to save the CreateDateTime when the UDFs are set. Is this posssible? It doesn't seem to work right now.
[PXTable(typeof(BAccount.bAccountID),IsOptional=true)]
public class CustomerExtension : PXCacheExtension<BAccount>
{
[PXDBCreatedDateTime()]
[PXUIField(DisplayName = "Date")]
public DateTime? CreatedDateTime { get; set; }
public class createdDateTime : IBqlField { }
}
I would assume it would not work as the BAccount table already contains a field with the same name 'CreatedDateTime'. I would first use a different field name for table extension fields as this could create some conflicts to those fields that already exist with the same name. Also, extension tables are inserted when the base table is either inserted or updated (first time after extension table is added) which may or may not occur from changes to your extension fields. This would also cause some issues for getting a good date from your PXDBCreatedDateTime field. You might be better off using a standard date time field and use some type of formula to update the date when your fields change. I would have to research the formula. You could use logic inside the setter of your user fields and add the PXDependsOnFields attribute to your date field and set your date field if null. I have not tried PXDependsOnFields in an extension - but the logic could be promising.

Map a flat structure to an object with AutoMapper?

The data being returned from a stored procedure has 3 columns of repeating data:
Name | Address | PhoneNumber | UniqueCol1 | UniqueCol2
Ideally I want my model to show that there is repeated data by only storing the values once and have a collection of the unique data.
public class MyViewModel
{
public string Name {get;set;}
public string Address {get;set;}
public string PhoneNumber {get;set;}
public List<MyModel> UniqueData {get;set;}
public class MyModel
{
public string UniqueCol1 {get;set;}
public string UniqueCol2 {get;set;}
}
}
This means I want to map a collection of results to a single object of MyViewModel:
return Mapper.Map<List<StoredProcedureObject>, MyViewModel>(result);
This is where I get my error as I assume I have some configuration that I need to do:
Mapping types:
List`1 -> MyViewModel
Any ideas on the missing step to get this to work?
Automapper is only able to flatten your structure into something simpler. But it's not possible to map a simple class to something more specific.
I would suggest to take only the first entry in your table to fill your base fields like Name, Address, PhoneNumber and iterate over your results to fill your UniqueData List.
I don't see an easier way, because with each possible mapping and without using seperate loops you will get your base data multiple times.
If you don't mind to use another tool, maybe you will have a look at ValueInjecter. I heard you can use this tool for two-way-mappings.

best practices with code or lookup tables

[UPDATE] Chosen approach is below, as a response to this question
Hi,
I' ve been looking around in this subject but I can't really find what I'm looking for...
With Code tables I mean: stuff like 'maritial status', gender, specific legal or social states... More specifically, these types have only set properties and the items are not about to change soon (but could). Properties being an Id, a name and a description.
I'm wondering how to handle these best in the following technologies:
in the database (multiple tables, one table with different code-keys...?)
creating the classes (probably something like inheriting ICode with ICode.Name and ICode.Description)
creating the view/presenter for this: there should be a screen containing all of them, so a list of the types (gender, maritial status ...), and then a list of values for that type with a name & description for each item in the value-list.
These are things that appear in every single project, so there must be some best practice on how to handle these...
For the record, I'm not really fond of using enums for these situations... Any arguments on using them here are welcome too.
[FOLLOW UP]
Ok, I've gotten a nice answer by CodeToGlory and Ahsteele. Let's refine this question.
Say we're not talking about gender or maritial status, wich values will definately not change, but about "stuff" that have a Name and a Description, but nothing more. For example: Social statuses, Legal statuses.
UI:
I want only one screen for this. Listbox with possibe NameAndDescription Types (I'll just call them that), listbox with possible values for the selected NameAndDescription Type, and then a Name and Description field for the selected NameAndDescription Type Item.
How could this be handled in View & Presenters? I find the difficulty here that the NameAndDescription Types would then need to be extracted from the Class Name?
DB:
What are pro/cons for multiple vs single lookup tables?
Using database driven code tables can very useful. You can do things like define the life of the data (using begin and end dates), add data to the table in real time so you don't have to deploy code, and you can allow users (with the right privileges of course) add data through admin screens.
I would recommend always using an autonumber primary key rather than the code or description. This allows for you to use multiple codes (of the same name but different descriptions) over different periods of time. Plus most DBAs (in my experience) rather use the autonumber over text based primary keys.
I would use a single table per coded list. You can put multiple codes all into one table that don't relate (using a matrix of sorts) but that gets messy and I have only found a couple situations where it was even useful.
Couple of things here:
Use Enumerations that are explicitly clear and will not change. For example, MaritalStatus, Gender etc.
Use lookup tables for items that are not fixed as above and may change, increase/decrease over time.
It is very typical to have lookup tables in the database. Define a key/value object in your business tier that can work with your view/presentation.
I have decided to go with this approach:
CodeKeyManager mgr = new CodeKeyManager();
CodeKey maritalStatuses = mgr.ReadByCodeName(Code.MaritalStatus);
Where:
CodeKeyManager can retrieve CodeKeys from DB (CodeKey=MaritalStatus)
Code is a class filled with constants, returning strings so Code.MaritalStatus = "maritalStatus". These constants map to to the CodeKey table > CodeKeyName
In the database, I have 2 tables:
CodeKey with Id, CodeKeyName
CodeValue with CodeKeyId, ValueName, ValueDescription
DB:
alt text http://lh3.ggpht.com/_cNmigBr3EkA/SeZnmHcgHZI/AAAAAAAAAFU/2OTzmtMNqFw/codetables_1.JPG
Class Code:
public class Code
{
public const string Gender = "gender";
public const string MaritalStatus = "maritalStatus";
}
Class CodeKey:
public class CodeKey
{
public Guid Id { get; set; }
public string CodeName { get; set; }
public IList<CodeValue> CodeValues { get; set; }
}
Class CodeValue:
public class CodeValue
{
public Guid Id { get; set; }
public CodeKey Code { get; set; }
public string Name { get; set; }
public string Description { get; set; }
}
I find by far the easiest and most efficent way:
All code-data can be displayed in a identical manner (in the same view/presenter)
I don't need to create tables and classes for every code table that's to come
But I can still get them out of the database easily and use them easily with the CodeKey constants...
NHibernate can handle this easily too
The only thing I'm still considering is throwing out the GUID Id's and using string (nchar) codes for usability in the business logic.
Thanks for the answers! If there are any remarks on this approach, please do!
I lean towards using a table representation for this type of data. Ultimately if you have a need to capture the data you'll have a need to store it. For reporting purposes it is better to have a place you can draw that data from via a key. For normalization purposes I find single purpose lookup tables to be easier than a multi-purpose lookup tables.
That said enumerations work pretty well for things that will not change like gender etc.
Why does everyone want to complicate code tables? Yes there are lots of them, but they are simple, so keep them that way. Just treat them like ever other object. Thy are part of the domain, so model them as part of the domain, nothing special. If you don't when they inevitibly need more attributes or functionality, you will have to undo all your code that currently uses it and rework it.
One table per of course (for referential integrity and so that they are available for reporting).
For the classes, again one per of course because if I write a method to recieve a "Gender" object, I don't want to be able to accidentally pass it a "MarritalStatus"! Let the compile help you weed out runtime error, that's why its there. Each class can simply inherit or contain a CodeTable class or whatever but that's simply an implementation helper.
For the UI, if it does in fact use the inherited CodeTable, I suppose you could use that to help you out and just maintain it in one UI.
As a rule, don't mess up the database model, don't mess up the business model, but it you wnt to screw around a bit in the UI model, that's not so bad.
I'd like to consider simplifying this approach even more. Instead of 3 tables defining codes (Code, CodeKey and CodeValue) how about just one table which contains both the code types and the code values? After all the code types are just another list of codes.
Perhaps a table definition like this:
CREATE TABLE [dbo].[Code](
[CodeType] [int] NOT NULL,
[Code] [int] NOT NULL,
[CodeDescription] [nvarchar](40) NOT NULL,
[CodeAbreviation] [nvarchar](10) NULL,
[DateEffective] [datetime] NULL,
[DateExpired] [datetime] NULL,
CONSTRAINT [PK_Code] PRIMARY KEY CLUSTERED
(
[CodeType] ASC,
[Code] ASC
)
GO
There could be a root record with CodeType=0, Code=0 which represents the type for CodeType. All of the CodeType records will have a CodeType=0 and a Code>=1. Here is some sample data that might help clarify things:
SELECT CodeType, Code, Description FROM Code
Results:
CodeType Code Description
-------- ---- -----------
0 0 Type
0 1 Gender
0 2 Hair Color
1 1 Male
1 2 Female
2 1 Blonde
2 2 Brunette
2 3 Redhead
A check constraint could be added to the Code table to ensure that a valid CodeType is entered into the table:
ALTER TABLE [dbo].[Code] WITH CHECK ADD CONSTRAINT [CK_Code_CodeType]
CHECK (([dbo].[IsValidCodeType]([CodeType])=(1)))
GO
The function IsValidCodeType could be defined like this:
CREATE FUNCTION [dbo].[IsValidCodeType]
(
#Code INT
)
RETURNS BIT
AS
BEGIN
DECLARE #Result BIT
IF EXISTS(SELECT * FROM dbo.Code WHERE CodeType = 0 AND Code = #Code)
SET #Result = 1
ELSE
SET #Result = 0
RETURN #Result
END
GO
One issue that has been raised is how to ensure that a table with a code column has a proper value for that code type. This too could be enforced by a check constraint using a function.
Here is a Person table which has a gender column. It could be a best practice to name all code columns with the description of the code type (Gender in this example) followed by the word Code:
CREATE TABLE [dbo].[Person](
[PersonID] [int] IDENTITY(1,1) NOT NULL,
[LastName] [nvarchar](40) NULL,
[FirstName] [nvarchar](40) NULL,
[GenderCode] [int] NULL,
CONSTRAINT [PK_Person] PRIMARY KEY CLUSTERED ([PersonID] ASC)
GO
ALTER TABLE [dbo].[Person] WITH CHECK ADD CONSTRAINT [CK_Person_GenderCode]
CHECK (([dbo].[IsValidCode]('Gender',[Gendercode])=(1)))
GO
IsValidCode could be defined this way:
CREATE FUNCTION [dbo].[IsValidCode]
(
#CodeTypeDescription NVARCHAR(40),
#Code INT
)
RETURNS BIT
AS
BEGIN
DECLARE #CodeType INT
DECLARE #Result BIT
SELECT #CodeType = Code
FROM dbo.Code
WHERE CodeType = 0 AND CodeDescription = #CodeTypeDescription
IF (#CodeType IS NULL)
BEGIN
SET #Result = 0
END
ELSE
BEGiN
IF EXISTS(SELECT * FROM dbo.Code WHERE CodeType = #CodeType AND Code = #Code)
SET #Result = 1
ELSE
SET #Result = 0
END
RETURN #Result
END
GO
Another function could be created to provide the code description when querying a table that has a code column. Here is an
example of querying the Person table:
SELECT PersonID,
LastName,
FirstName,
GetCodeDescription('Gender',GenderCode) AS Gender
FROM Person
This was all conceived from the perspective of preventing the proliferation of lookup tables in the database and providing one lookup table. I have no idea whether this design would perform well in practice.

Resources