精华内容
下载资源
问答
  • Cinchoo ETL - JSON Writer

    2020-08-03 00:07:35
    下载源代码 下载编译文件 (.NET Framework) 下载编译文件 (.NET Standard / .NET Core) ...自定义JSON记录8。自定义JSON字段 8.1。defaultvalue 8.2。chofallbackvalue 8.3。类型转换器 8.3.1。8.3.2声明性方法
    下载源代码	下载编译文件 (.NET Framework)	下载编译文件 (.NET Standard / .NET Core)
    

    内容

    1. 介绍2。要求3。“Hello World !”样本

    3.1。快速写入-数据优先方法3.2。代码优先方法3.3。Configuration First 方法
    4. 记录所有记录Write 记录手动6。自定义JSON记录8。自定义JSON字段

    8.1。defaultvalue 8.2。chofallbackvalue 8.3。类型转换器

    8.3.1。8.3.2声明性方法。8.3.3配置方法。自定义值转换器方法
    8.4。验证8.5。choignoremember 8.6。stringlength 8.6。显示8.7。DisplayName
    10. 回调机制

    10.1使用JSONWriter events 10.2 实现IChoNotifyRecordWrite接口10.1 beginwrite 10.2 endwrite 10.3 beforerecordwrite 10.4 afterrecordwrite 10.5 recordwriteerror 10.6 beforerecordfieldwrite 10.7 afterrecordfieldwrite 10.8 RecordWriteFieldError
    11. 定制12。使用动态对象13。异常15。使用元类型注释16。配置选择

    手动配置16.2自动映射配置16.3附加元类型类
    17. ToTextAll Helper方法17a。18 ToText 辅助方法。写datareaderhelper方法19。编写DataTable Helper方法20。高级的主题

    重写转换器格式规范20.2货币支持20.3枚举支持20.4布尔值支持20.5日期时间支持
    21. 流利的API

    21.1。nullvalue处理21.2. 格式化21.3与字段21.4 与字段21.5. ignorefieldvaluemode 21.6 columncountstrict 21.7。配置21.8。设置
    22. 常见问题解答

    22.1。如何序列化一个对象?22.2。如何序列化对象的集合?22.3。如何序列化动态对象?22.4。如何序列化匿名对象?22.5。如何序列化集合?22.6。如何序列化字典?22.7。如何序列化数据表?22.8。如何序列化JSON到一个文件?22.9。如何序列化未缩进的JSON?22.10。如何序列化条件属性?22.11。如何序列化的日期时间在自定义日期格式?如何从Json序列化中排除属性?22.13.如何将Xml转换成JSON?22.14.如何将CSV转换成JSON?

    1. 介绍

    ChoETL是一个用于。net的开放源码ETL(提取、转换和加载)框架。它是一个基于代码的库,用于在。net环境中从多个数据源提取数据、转换并加载到自己的数据仓库中。您可以在数据仓库中立即拥有数据。

    本文讨论如何使用ChoETL框架提供的ChoJSONWriter组件。它是一个将JSON数据保存到文件/外部数据源的简单实用程序类。

    相应的ChoJSONReader,一篇JSON阅读器文章可以在这里找到。

    特点:

    遵循JSON标准文件规则。在生成文件时支持区域性特定的日期、货币和数字格式。支持不同的字符编码。提供良好的控制日期,货币,枚举,布尔,数字格式时写文件。详细和健壮的错误处理,允许您快速发现和修复问题。缩短开发时间。

    1. 要求

    这个框架库是用c#编写的,使用。net 4.5 framework /。net core 2.x。

    3.“Hello World !”样本

    创建一个示例VS.NET(。NET Framework 4.5)控制台应用程序项目安装ChoETL via Package Manager consoleusingnuget命令基于工作。NET版本:

    安装包ChoETL。json安装包ChoETL.JSON.NETStandard
    使用ChoETL名称空间

    让我们从一个简单的示例开始,该示例生成下面有两列的JSON文件

    清单3.1示例JSON数据文件(emp.json)

    隐藏,复制Code[
    {
    “Id”: 1,
    “Name”: “Mark”
    },
    {
    “Id”: 2,
    “Name”: “Jason”
    }
    ]

    有许多方法可以通过最小的设置创建JSON文件。

    3.1。快速写入-数据优先方法

    这是一种从零开始配置的快速创建JSON文件的方法。不需要任何类型的POCO对象。下面的示例代码展示了如何使用动态对象生成示例JSON文件

    清单3.1.1将对象列表写入JSON文件

    隐藏,复制CodeList objs = new List();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 1;
    rec1.Name = “Mark”;
    objs.Add(rec1);

    dynamic rec2 = new ExpandoObject();
    rec2.Id = 2;
    rec2.Name = “Jason”;
    objs.Add(rec2);

    using (var parser = new ChoJSONWriter(“emp.json”))
    {
    parser.Write(objs);
    }

    在上面的示例中,我们将动态对象列表一次性提供给JSONWriter,以便将它们写入JSON文件。

    清单3.1.2将每个对象写入JSON文件

    隐藏,复制Codeusing (var parser = new ChoJSONWriter(“emp.json”))
    {
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 1;
    rec1.Name = “Mark”;
    parser.Write(item);

    dynamic rec1 = new ExpandoObject();
    rec1.Id = 2;
    rec1.Name = "Jason";
    parser.Write(item);
    

    }

    在上面的示例中,我们控制构造,将每个动态记录传递给JSONWriter,以使用写重载生成JSON文件。

    3.2。代码首先方法

    这是使用类型化POCO类生成JSON文件的另一种zeo-config方法。首先定义一个简单的POCO类来匹配底层JSON文件布局

    清单3.2.1简单的POCO实体类

    隐藏,复制Codepublic partial class EmployeeRecSimple
    {
    public int Id { get; set; }
    public string Name { get; set; }
    }

    在上面,POCO类定义了两个与示例JSON文件模板匹配的属性。

    清单3.2.2保存为JSON文件

    隐藏,复制CodeList objs = new List();

    EmployeeRecSimple rec1 = new EmployeeRecSimple();
    rec1.Id = 1;
    rec1.Name = “Mark”;
    objs.Add(rec1);

    EmployeeRecSimple rec2 = new EmployeeRecSimple();
    rec2.Id = 2;
    rec2.Name = “Jason”;
    objs.Add(rec2);

    using (var parser = new ChoJSONWriter(“emp.json”))
    {
    parser.Write(objs);
    }

    上面的示例展示了如何创建来自类型化POCO类对象的JSON文件。

    3.3。Configuration First 方法

    在这个模型中,我们定义了JSON配置,包括所有必需的参数以及生成示例JSON文件所需的JSON列。

    清单3.3.1定义JSON配置

    隐藏,复制CodeChoJSONRecordConfiguration config = new ChoJSONRecordConfiguration();
    config.JSONRecordFieldConfigurations.Add(new ChoJSONRecordFieldConfiguration(“Id”));
    config.JSONRecordFieldConfigurations.Add(new ChoJSONRecordFieldConfiguration(“Name”));

    在上面,类定义了两个与示例JSON文件模板匹配的JSON属性。

    清单3.3.2生成没有POCO对象的JSON文件

    隐藏,复制CodeList objs = new List();

    dynamic rec1 = new ExpandoObject();
    rec1.Id = 1;
    rec1.Name = “Mark”;
    objs.Add(rec1);

    dynamic rec2 = new ExpandoObject();
    rec2.Id = 2;
    rec2.Name = “Jason”;
    objs.Add(rec2);

    using (var parser = new ChoJSONWriter(“emp.json”, config))
    {
    parser.Write(objs);
    }

    上面的示例代码展示了如何使用预定义的JSON配置设置从动态对象列表生成JSON文件。在JSONWriter构造函数中,我们指定了JSON配置配置对象,以便在创建文件时遵循JSON布局模式。如果JSON列的名称或计数不匹配,将报告为错误并停止写入过程。

    清单3.3.3使用POCO对象保存JSON文件

    隐藏,复制CodeList objs = new List();

    EmployeeRecSimple rec1 = new EmployeeRecSimple();
    rec1.Id = 1;
    rec1.Name = “Mark”;
    objs.Add(rec1);

    EmployeeRecSimple rec2 = new EmployeeRecSimple();
    rec2.Id = 2;
    rec2.Name = “Jason”;
    objs.Add(rec2);

    using (var parser = new ChoJSONWriter(“emp.json”, config))
    {
    parser.Write(objs);
    }

    上面的示例代码展示了如何使用JSON配置对象从POCO对象列表生成JSON文件。在JSONWriter构造函数中,我们指定了JSON配置配置对象。

    3.4。首先使用声明式配置编写代码

    这是定义POCO实体类和声明性附加JSON配置参数的组合方法。id是required列,name是可选值列,默认值为“XXXX”。如果名称不存在,它将采用默认值。

    清单3.4.1定义POCO对象

    隐藏,复制Codepublic class EmployeeRec
    {
    [ChoJSONRecordField]
    [Required]
    public int? Id
    {
    get;
    set;
    }

    [ChoJSONRecordField]
    [DefaultValue("XXXX")]
    public string Name
    {
        get;
        set;
    }
    
    public override string ToString()
    {
        return "{0}. {1}.".FormatString(Id, Name);
    }
    

    }

    上面的代码演示了如何用生成JSON文件所需的nessasary属性定义POCO对象。首先使用ChoJSONRecordFieldAttribute为每个记录字段定义属性,以符合JSON记录映射。Id是必需的属性。我们用要求的贡品装饰了它。Name使用DefaultValueAttribute为其提供默认值。这意味着如果对象中没有设置名称值,JSONWriter就会将默认值‘XXXX’发送给文件。

    它非常简单,可以立即保存JSON数据。

    清单3.4.2使用POCO对象保存JSON文件

    隐藏,复制CodeList objs = new List();

    EmployeeRec rec1 = new EmployeeRec();
    rec1.Id = 1;
    rec1.Name = “Mark”;
    objs.Add(rec1);

    EmployeeRec rec2 = new EmployeeRec();
    rec2.Id = 2;
    rec2.Name = “Jason”;
    objs.Add(rec2);

    using (var parser = new ChoJSONWriter(“emp.json”))
    {
    parser.Write(objs);
    }

    我们首先创建一个chojsonwriterobject的新实例。这是所有。所有从对象生成JSON数据的繁重工作都是由编写器在幕后完成的。

    默认情况下,JSONWriter 在保存JSON文件时发现并使用默认配置参数。这些可以根据您的需要进行包装。下面几节将详细介绍每个配置属性。

    1. 写所有的记录

    设置与JSON文件结构匹配的POCO对象,构造对象列表并将其传递给JSONWriter的Write方法,就像这样简单。这将在一次调用中将整个对象列表写入JSON文件。

    清单4.1写入JSON文件

    隐藏,复制CodeList objs = new List();
    //Construct and attach objects to this list

    using (var parser = new ChoJSONWriter(“emp.json”))
    {
    parser.Write(objs);
    }

    或者:

    清单4.2编写器到JSON文件流

    隐藏,复制CodeList objs = new List();
    //Construct and attach objects to this list

    using (var tx = File.OpenWrite(“emp.json”))
    {
    using (var parser = new ChoJSONWriter(tx))
    {
    parser.Write(objs);
    }
    }

    这个模型使您的代码优雅、干净、易于阅读和维护。

    1. Write 手动记录

    当POCO对象以一种断开连接的方式构造时,这是一种将每条记录写入JSON文件的替代方法。

    清单5.1编写JSON文件

    隐藏,复制Codevar writer = new ChoJSONWriter(“emp.json”);

    EmployeeRec rec1 = new EmployeeRec();
    rec1.Id = 1;
    rec1.Name = “Mark”;

    writer.Write(rec1);

    EmployeeRec rec2 = new EmployeeRec();
    rec1.Id = 2;
    rec1.Name = “Jason”;

    writer.Write(rec2);

    1. 自定义JSON记录

    使用ChoJSONRecordObjectAttribute,您可以声明地定制POCO实体对象。

    清单6.1为每条记录定制POCO对象

    隐藏,复制Code[ChoJSONRecordObject]
    public class EmployeeRec
    {
    [ChoJSONRecordField]
    public int Id { get; set; }
    [ChoJSONRecordField]
    [Required]
    [DefaultValue(“ZZZ”)]
    public string Name { get; set; }
    }

    下面是对文件执行JSON加载操作定制的可用属性。

    文化——用于读写的文化信息。ColumnCountStrict——此标志指示如果JSON字段配置与数据对象成员不匹配,是否应抛出异常。特殊的空值文本期望被处理为空值从JSON文件在记录级别。ErrorMode——此标志指示如果写入操作和预期字段写入失败时是否应抛出异常。这可以被每个属性覆盖。可能的值是:

    IgnoreAndContinue—忽略错误,记录将被跳过并继续next。ReportAndContinue -向POCO实体报告错误,如果它是IChoNotifyRecordWrite类型throwandstop -抛出错误并停止执行
    IgnoreFieldValueMode - N / A。ObjectValidationMode——一个让读者知道记录对象执行的验证类型的标志。可能的值是:

    Off -没有执行对象验证。(默认)memberlevel——在将每个JSON属性写入文件之前执行验证。ObjectLevel —在将所有POCO属性写入文件之前执行验证。

    1. 自定义JSON字段

    对于每个JSON列,您可以使用ChoJSONRecordFieldAttribute在POCO实体属性中指定映射。

    清单6.1为JSON列定制POCO对象

    隐藏,复制Codepublic class EmployeeRec
    {
    [ChoJSONRecordField]
    public int Id { get; set; }
    [ChoJSONRecordField]
    [Required]
    [DefaultValue(“ZZZ”)]
    public string Name { get; set; }
    }

    这是可用的会员为每个属性添加一些自定义:

    FieldName—JSON字段名。如果没有指定,POCO对象属性名将被用作字段名。大小——JSON列值的大小。NullValue —特殊的空值文本期望在字段级别上作为JSON文件中的空值处理。ErrorMode——这个标志指示如果写入和预期字段转换和写入失败,是否应该抛出异常。可能的值是:

    IgnoreAndContinue—忽略错误并继续加载记录的其他属性。ReportAndContinue——如果POCO实体是IChoRecord类型,则向它报告错误。Throw and stop—抛出错误并停止执行。

    8.1。DefaultValue

    任何POCO实体属性都可以使用System.ComponentModel.DefaultValueAttribute用默认值指定。当JSON值为null时(通过IgnoreFieldValueMode控制),它是用于写入的值。

    8.2。ChoFallbackValue

    可以使用choet . chofallbackvalueattribute用回退值指定任何POCO实体属性。它是当属性无法写入JSON时使用的值。回退值仅在ErrorMode为IgnoreAndContinue或ReportAndContinue时设置。

    8.3。类型转换器

    大多数基本类型会自动转换为string/text并保存为JSON文件。如果JSON字段的值不能自动转换为文本值,可以指定一个自定义/内置的. net转换器来将值转换为文本。这些可以是IValueConverter、IChoValueConverteror TypeConverter转换器。

    有两种方法可以为每个字段指定转换器

    声明式方法配置方法

    8.3.1。声明式方法

    此模型仅适用于poco实体对象。如果您有POCO 类,您可以为每个属性指定转换器,以对它们执行必要的转换。下面的示例展示了实现方法。

    清单8.3.1.1指定类型转换器

    隐藏,复制Codepublic class EmployeeRec
    {
    [ChoJSONRecordField]
    [ChoTypeConverter(typeof(IntConverter))]
    public int Id { get; set; }
    [ChoJSONRecordField]
    [Required]
    [DefaultValue(“ZZZ”)]
    public string Name { get; set; }
    }

    清单8.3.1.2 IntConverter实现

    隐藏,复制Codepublic class IntConverter : IValueConverter
    {
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
    return value;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        int intValue = (int)value;
        return intValue.ToString("D4");
    }
    

    }

    在上面的例子中,我们定义了自定义的IntConverter类。并演示了如何用前导零格式化’Id’ JSON属性。

    8.3.2。的配置方法

    此模型既适用于动态对象,也适用于poco&entity对象。这样就可以在运行时将转换器附加到每个属性上。这优先于POCO类上的声明式转换器。

    清单8.3.2.1 指定TypeConverters

    隐藏,复制CodeChoJSONRecordConfiguration config = new ChoJSONRecordConfiguration();

    ChoJSONRecordFieldConfiguration idConfig = new ChoJSONRecordFieldConfiguration(“Id”);
    idConfig.AddConverter(new IntConverter());
    config.JSONRecordFieldConfigurations.Add(idConfig);

    config.JSONRecordFieldConfigurations.Add(new ChoJSONRecordFieldConfiguration(“Name”));
    config.JSONRecordFieldConfigurations.Add(new ChoJSONRecordFieldConfiguration(“Name1”));

    在上面,我们使用chojsonrecordfieldconfigurationobject中的AddConverter助手方法构造并将IntConverter附加到’Id’字段。

    同样,如果您想从其中删除任何转换器,您可以在ChoJSONRecordFieldConfiguration对象上使用RemoveConverter。

    8.3.3。自定义值转换器方法

    这种方法允许使用Fluenrt API将值转换器附加到每个JSON成员。这是处理任何奇怪的转换过程并避免创建值转换器类的快速方法。

    清单8.3.3.1 少类

    隐藏,复制Codepublic class EmployeeRec
    {
    [ChoJSONRecordField]
    public int Id { get; set; }
    [ChoJSONRecordField(2, FieldName =“Name”, QuoteField = true)]
    [Required]
    [DefaultValue(“ZZZ”)]
    public string Name { get; set; }
    }

    使用fluent API,下面的示例将展示如何将值转换器附加到Id列

    清单8.3.3.2附加值转换器

    隐藏,复制Codeusing (var dr = new ChoJSONWriter(@“Test.json”)
    .WithField(c => c.Id, valueConverter: (v) => ((int)value).ToString(“C3”, CultureInfo.CurrentCulture))
    )
    {
    Console.WriteLine(rec);
    }

    8.4。验证

    JSONWriter利用both System.ComponentModel。DataAnnotations和Validation Block 验证属性为POCO实体的各个字段指定验证规则。参考MSDN站点获取可用的DataAnnotations验证属性列表。

    清单8.4.1在POCO实体中使用验证属性

    隐藏,复制Code[ChoJSONRecordObject]
    public partial class EmployeeRec
    {
    [ChoJSONRecordField(1, FieldName = “id”)]
    [ChoTypeConverter(typeof(IntConverter))]
    [Range(1, int.MaxValue, ErrorMessage = “Id must be > 0.”)]
    [ChoFallbackValue(1)]
    public int Id { get; set; }

    [ChoJSONRecordField]
    [Required]
    [DefaultValue("ZZZ")]
    [ChoFallbackValue("XXX")]
    public string Name { get; set; }
    

    }

    在上面的例子中,使用range验证属性来验证属性。需要验证属性来命名属性。配置时,JSONWriter在将数据保存到文件之前对它们执行验证。ObjectValidationMode设置为ChoObjectValidationMode。MemberLevel或ChoObjectValidationMode.ObjectLevel。

    在某些情况下,您可能想在POCO实体类中控制和执行手动的自我验证。这可以通过从IChoValidatable接口继承POCO对象来实现。

    清单8.4.2对POCO实体进行手工验证

    隐藏,复制Code[ChoJSONRecordObject]
    public partial class EmployeeRec : IChoValidatable
    {
    [ChoJSONRecordField]
    [ChoTypeConverter(typeof(IntConverter))]
    [Range(1, int.MaxValue, ErrorMessage = “Id must be > 0.”)]
    [ChoFallbackValue(1)]
    public int Id { get; set; }

    [ChoJSONRecordField]
    [Required]
    [DefaultValue("ZZZ")]
    [ChoFallbackValue("XXX")]
    public string Name { get; set; }
    
    public bool TryValidate(object target, ICollection<ValidationResult> validationResults)
    {
        return true;
    }
    
    public bool TryValidateFor(object target, string memberName, ICollection<ValidationResult> validationResults)
    {
        return true;
    }
    

    }

    上面的示例展示了如何在POCO对象中实现自定义验证。

    IChoValidatable接口公开了下面的方法

    TryValidate—验证整个对象,如果所有验证都通过,则返回true。否则返回假。TryValidateFor -验证对象的特定属性,如果所有验证都通过,则返回true。否则返回假。

    8.5。ChoIgnoreMember

    如果您想在optout模式下忽略JSON解析中的POCO类成员,请使用ChoIgnoreMemberAttribute对其进行修饰。下面的示例显示标题成员在JSON加载过程中被忽略。

    清单8.5.1忽略一个成员

    Hide ,复制代码

    隐藏,复制Codepublic class EmployeeRec
    {
    public int Id { get; set; }
    public string Name { get; set; }
    [ChoIgnoreMember]
    public string Title { get; set; }
    }

    8.6。StringLength

    在选择在输出模式下,您可以通过使用System.ComponentModel.DataAnnotations.StringLengthAttribute. 来指定JSON列的大小。

    清单8.6.1指定JSON成员的大小

    Hide ,复制代码

    隐藏,复制Codepublic class EmployeeRec
    {
    public int Id { get; set; }
    [StringLength(25)]
    public string Name { get; set; }
    [ChoIgnoreMember]
    public string Title { get; set; }
    }

    8.6。显示

    在OptOut模式下,您可以使用System.ComponentModel.DataAnnotations.DisplayAttribute. 指定JSON列映射到成员的名称。

    清单8.6.1指定JSON列的名称

    Hide ,复制代码

    隐藏,复制Codepublic class EmployeeRec
    {
    public int Id { get; set; }
    [Display(Name=“FullName”)]
    [StringLength(25)]
    public string Name { get; set; }
    [ChoIgnoreMember]
    public string Title { get; set; }
    }

    8.7。DisplayName

    在OptOut模式下,您可以指定JSON列的名称映射到成员使用System.ComponentModel.DataAnnotations.DisplayNameAttribute.

    清单8.7.1指定JSON列的名称

    隐藏,复制Codepublic class EmployeeRec
    {
    public int Id { get; set; }
    [Display(Name=“FullName”)]
    [StringLength(25)]
    public string Name { get; set; }
    [ChoIgnoreMember]
    public string Title { get; set; }
    }

    1. 回调机制

    JSONWriter提供了开箱即用的行业标准JSON数据文件生成,以处理大多数需求。如果生成过程不处理您的任何需求,您可以使用JSONWriter 提供的回调机制来处理这种情况。为了参与回调机制,您可以使用以下任一种模型

    使用JSONWriter通过IChoWriter接口公开的事件处理程序。通过IChoNotifyRecordWrite / IChoNotifyRecordFieldWrite 接口继承DataAnnotation的元类型对象。

    为了参与回调机制,POCO实体对象或DataAnnotation的元类型对象都必须被ichonotifyrecordwriteinterface继承。

    提示:从这些接口方法中引发的任何异常都将被忽略。

    ichorecorder公开了以下方法:

    BeginWrite——调用JSON文件编写endwrite的开始——结束时调用JSON文件写beforerecordwrite ——提高JSON记录写afterrecordwrite - JSON记录写recordwriteerror后提出提高当JSON记录错误而写作beforerecordfieldwrite - JSON列值写afterrecordfieldwrite之前提出提高JSON之后列值写recordfieldwriteerror——当JSON列值的错误while 写作

    IChoNotifyRecordWrite 暴露以下方法:

    BeforeRecordWrite -在JSON记录写入之前提出,afterrecordwritewritewrite -在JSON记录写入错误时提出

    IChoNotifyFileWrite 暴露以下方法:

    BeginWrite -调用在JSON文件的开始写结束

    IChoNotifyRecordFieldWrite 暴露以下方法:

    BeforeRecordFieldWrite -在JSON列值写入后上升recordfieldwriteerror -当JSON列值写入错误时上升

    IChoNotifyFileHeaderArrange 暴露以下方法:

    FileHeaderArrange —在JSON文件头被写入文件之前引发,一个重新排列JSON列的机会

    IChoNotifyFileHeaderWrite 暴露以下方法:

    FileHeaderWrite -在JSON文件头被写入文件之前引发,一个定制头的机会。

    10.1使用JSONWriter事件

    这是订阅回调事件和处理解析JSON文件时奇怪情况的更直接和最简单的方法。缺点是代码不能像使用POCO记录对象实现ichonotifyrecor惧那样可重用。

    下面的示例展示了如何使用beforerecordloadcallback方法跳过含有’%'字符的语句行。

    清单10.1.1使用JSONWriter回调事件

    隐藏,复制Codestatic void IgnoreLineTest()
    {
    using (var parser = new ChoJSONWriter(“emp.json”))
    {
    parser.BeforeRecordWrite += (o, e) =>
    {
    if (e.Source != null)
    {
    e.Skip = ((JObject)e.Source).Contains(“name1”);
    }
    };

        parser.Write(rec);
    }
    

    }

    同样,您也可以在JSONWriter中使用其他回调方法。

    10.2实现IChoNotifyRecordWrite接口

    下面的示例展示了如何实现ichonotifyrecordwriteinterface来指导POCO类。

    清单10.2.1直接POCO回调机制实现

    隐藏,收缩,复制Code[ChoJSONRecordObject]
    public partial class EmployeeRec : IChoNotifyrRecordWrite
    {
    [ChoJSONRecordField]
    [ChoTypeConverter(typeof(IntConverter))]
    [Range(1, int.MaxValue, ErrorMessage = “Id must be > 0.”)]
    [ChoFallbackValue(1)]
    public int Id { get; set; }

    [ChoJSONRecordField]
    [Required]
    [DefaultValue("ZZZ")]
    [ChoFallbackValue("XXX")]
    public string Name { get; set; }
    
    public bool AfterRecordWrite(object target, int index, object source)
    {
        throw new NotImplementedException();
    }
    
    public bool BeforeRecordWrite(object target, int index, ref object source)
    {
        throw new NotImplementedException();
    }
    
    public bool RecordWriteError(object target, int index, object source, Exception ex)
    {
        throw new NotImplementedException();
    }
    

    }

    下面的示例展示了如何通过在POCO类上使用MetadataTypeAttribute将元数据类附加到它。

    清单10.2.2基于元类型的回调机制实现

    隐藏,收缩,复制Code[ChoJSONRecordObject]
    public class EmployeeRecMeta : IChoNotifyRecordWrite
    {
    [ChoJSONRecordField]
    [ChoTypeConverter(typeof(IntConverter))]
    [Range(1, int.MaxValue, ErrorMessage = “Id must be > 0.”)]
    [ChoFallbackValue(1)]
    public int Id { get; set; }

    [ChoJSONRecordField]
    [Required]
    [DefaultValue("ZZZ")]
    [ChoFallbackValue("XXX")]
    public string Name { get; set; }
    
    public bool AfterRecordWrite(object target, int index, object source)
    {
        throw new NotImplementedException();
    }
    
    public bool BeforeRecordWrite(object target, int index, ref object source)
    {
        throw new NotImplementedException();
    }
    
    public bool RecordWriteError(object target, int index, object source, Exception ex)
    {
        throw new NotImplementedException();
    }
    

    }

    [MetadataType(typeof(EmployeeRecMeta))]
    public partial class EmployeeRec
    {
    public int Id { get; set; }
    public string Name { get; set; }
    }

    下面的示例展示了如何通过在其上使用ChoMetadataRefTypeAttribute为密封的或第三方POCO类附加元数据类。

    清单10.2.2基于元类型的回调机制实现

    隐藏,收缩,复制Code[ChoMetadataRefType(typeof(EmployeeRec))]
    [ChoJSONRecordObject]
    public class EmployeeRecMeta : IChoNotifyRecordWrite
    {
    [ChoJSONRecordField]
    [ChoTypeConverter(typeof(IntConverter))]
    [Range(1, int.MaxValue, ErrorMessage = “Id must be > 0.”)]
    [ChoFallbackValue(1)]
    public int Id { get; set; }

    [ChoJSONRecordField]
    [Required]
    [DefaultValue("ZZZ")]
    [ChoFallbackValue("XXX")]
    public string Name { get; set; }
    
    public bool AfterRecordWrite(object target, int index, object source)
    {
        throw new NotImplementedException();
    }
    
    public bool BeforeRecordWrite(object target, int index, ref object source)
    {
        throw new NotImplementedException();
    }
    
    public bool RecordWriteError(object target, int index, object source, Exception ex)
    {
        throw new NotImplementedException();
    }
    

    }

    public partial class EmployeeRec
    {
    public int Id { get; set; }
    public string Name { get; set; }
    }

    10.1 BeginWrite

    这个回调在JSON文件写入开始时调用一次。source是JSON文件流对象。在这里,您有机会检查流,返回true以继续JSON生成。用谎言来阻止一代人。

    Listing 大家BeginWrite 调样品

    隐藏之处;复制Codepublic bool BeginWrite(object source)
    {
    StreamReader sr = source as StreamReader;
    return true;
    }

    10.2 EndWrite

    这个回调在JSON文件生成结束时调用一次。source是JSON文件流对象。在这里,你有机会检查流,做任何张贴步骤,以执行的流。

    Listing 10.2.1 EndWrite 调样品

    隐藏,复制Codepublic void EndWrite(object source)
    {
    StreamReader sr = source as StreamReader;
    }

    10.3 BeforeRecordWrite

    这个回调在每个POCO记录对象被写入JSON文件之前被调用。目标是POCO记录对象的实例。index是文件中的行索引。source是JSON记录行。在这里,您有机会检查POCO对象,并在需要时生成JSON记录行。

    提示:如果您想要跳过写入记录,请将源设置为null。

    返回true继续加载进程,否则返回false停止进程。

    Listing 10.3.1 BeforeRecordWrite 调样品

    隐藏,复制Codepublic bool BeforeRecordWrite(object target, int index, ref object source)
    {
    return true;
    }

    10.4 AfterRecordWrite

    这个回调是在每个POCO记录对象被写入JSON文件之后调用的。target是POCO记录对象的实例。index是文件中的行索引。source是JSON记录行。在这里,你有机会用记录线做任何后步操作。

    返回true继续加载进程,否则返回false停止进程。

    清单10.4.1 AfterRecordWrite回调示例

    隐藏,复制Codepublic bool AfterRecordWrite(object target, int index, object source)
    {
    return true;
    }

    10.5 RecordWriteError

    如果在写POCO记录对象时遇到错误,这个回调函数就会被调用。target是POCO记录对象的实例。index是文件中的行索引。source是JSON记录行。ex是异常对象。在这里,你有机会处理异常。此方法仅在配置时调用。ErrorMode ReportAndContinue。

    返回true继续加载进程,否则返回false停止进程。

    清单10.5.1 RecordWriteError回调示例

    隐藏,复制Codepublic bool RecordLoadError(object target, int index, object source, Exception ex)
    {
    return true;
    }

    10.6 BeforeRecordFieldWrite

    这个回调在每个JSON记录列被写入JSON文件之前被调用。target是POCO记录对象的实例。index是文件中的行索引,propName 是JSON记录的属性名。value 是JSON列的值。在这里,你有机会检查JSON记录属性值和执行任何自定义验证等。

    返回true继续加载进程,否则返回false停止进程。

    清单10.6.1 BeforeRecordFieldWrite回调示例

    隐藏,复制Codepublic bool BeforeRecordFieldWrite(object target, int index, string propName, ref object value)
    {
    return true;
    }

    10.7 AfterRecordFieldWrite

    这个回调在每个JSON 记录列值被写入JSON文件之后调用。target是POCO记录对象的实例。index是文件中的行索引,propName 是JSON记录的属性名。value是JSON列的值。任何post字段操作都可以在这里执行,比如计算其他属性、验证等。

    返回true继续加载进程,否则返回false停止进程。

    清单10.7.1 AfterRecordFieldWrite回调示例

    隐藏,复制Codepublic bool AfterRecordFieldWrite(object target, int index, string propName, object value)
    {
    return true;
    }

    10.8 RecordWriteFieldError

    当写入json记录列值时遇到错误时调用这个回调函数。target是POCO记录对象的实例。index是文件中的行index propName 是JSON记录属性名。value是JSON列的值。ex是异常对象。在这里,你有机会处理异常。该方法仅在JSONWriter执行以下两组步骤之后调用

    JSONWriter查找每个JSON属性的回退值。如果有的话,它试着用它来写作。如果FallbackValue值不存在,则配置。错误模式被指定为ReportAndContinue。,此回调将被执行。

    返回true继续加载进程,否则返回false停止进程。

    清单10.8.1 RecordFieldWriteError回调示例

    隐藏,复制Codepublic bool RecordFieldWriteError(object target, int index, string propName, object value, Exception ex)
    {
    return true;
    }

    1. 定制

    JSONWriter自动从POCO实体检测和加载配置设置。在运行时,您可以在生成JSON之前定制和调整这些参数。JSONWriter公开配置属性,它属于ChoJSONRecordConfiguration对象。使用此属性,您可以执行定制。

    清单11.1在运行时定制JSONWriter

    隐藏,复制Codeclass Program
    {
    static void Main(string[] args)
    {
    List objs = new List();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 1;
    rec1.Name = “Mark”;
    objs.Add(rec1);

        dynamic rec2 = new ExpandoObject();
        rec2.Id = 2;
        rec2.Name = "Jason";
        objs.Add(rec2);
    
        using (var parser = new ChoJSONWriter("emp.json"))
        {
            parser.Configuration.ColumnCountStrict = true;
            parser.Write(objs);
        }
    }
    

    }

    1. 使用动态对象

    到目前为止,本文解释了如何使用JSONWriter和POCO对象。JSONWriter还支持生成没有POCO实体对象的JSON文件,它利用了。net动态特性。下面的示例展示了如何使用动态对象生成JSON流。JSON模式是从第一个对象确定的。如果在动态对象成员值中发现不匹配,则会引发错误并停止生成过程。

    下面的例子可以说明:

    清单12.1从动态对象生成JSON文件

    嗨德,复制Codeclass Program
    {
    static void Main(string[] args)
    {
    List objs = new List();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 1;
    rec1.Name = “Mark”;
    objs.Add(rec1);

        dynamic rec2 = new ExpandoObject();
        rec2.Id = 2;
        rec2.Name = "Jason";
        objs.Add(rec2);
    
        using (var parser = new ChoJSONWriter("emp.json"))
        {
            parser.Configuration.ColumnCountStrict = true;
            parser.Write(objs);
        }
    }
    

    }

    1. 异常

    JSONWriter在不同的情况下抛出不同类型的异常。

    JSON文件坏了,解析器无法恢复。ChoRecordConfigurationException -指定任何无效配置设置时,将引发此异常。ChoMissingRecordFieldException—JSON列缺少一个属性,将引发此异常。

    1. 使用MetadataType注释

    Cinchoo ETL与数据注释的元类型模型一起工作得更好。这是将元数据类附加到数据模型类的方法。在这个关联类中,您提供了数据模型中没有的附加元数据信息。It角色是在不修改类的情况下向类添加属性。您可以将这个带有单个参数的属性添加到具有所有属性的类中。当POCO类由自动工具自动生成(由实体框架、MVC等)时,这是很有用的。这就是为什么第二节课起作用了。您可以在不修改生成的文件的情况下添加新内容。通过将关注点分离到多个类,这也促进了模块化。

    更多信息,请在MSDN搜索。

    清单15.1元类型注释使用示例

    隐藏,收缩,复制Code[MetadataType(typeof(EmployeeRecMeta))]
    public class EmployeeRec
    {
    public int Id { get; set; }
    public string Name { get; set; }
    }

    [ChoJSONRecordObject]
    public class EmployeeRecMeta : IChoNotifyRecordWrite, IChoValidatable
    {
    [ChoJSONRecordField]
    [ChoTypeConverter(typeof(IntConverter))]
    [Range(1, 1, ErrorMessage = “Id must be > 0.”)]
    [ChoFallbackValue(1)]
    public int Id { get; set; }

    [ChoJSONRecordField]
    [StringLength(1)]
    [DefaultValue("ZZZ")]
    [ChoFallbackValue("XXX")]
    public string Name { get; set; }
    
    public bool AfterRecordWrite(object target, int index, object source)
    {
        throw new NotImplementedException();
    }
    
    public bool BeforeRecordWrite(object target, int index, ref object source)
    {
        throw new NotImplementedException();
    }
    
    public bool RecordWriteError(object target, int index, object source, Exception ex)
    {
        throw new NotImplementedException();
    }
    
    public bool TryValidate(object target, ICollection<ValidationResult> validationResults)
    {
        return true;
    }
    
    public bool TryValidateFor(object target, string memberName, ICollection<ValidationResult> validationResults)
    {
        return true;
    }
    

    }

    在上面,雇员建立是数据类。只包含特定于域的属性和操作。将它标记为非常简单的类。

    我们将验证、回调机制、配置等分离为元数据类型类、EmployeeRecMeta。

    1. 配置选择

    如果POCO entity类是自动生成的类或通过库公开的类,或者它是密封的类,那么它会限制您以声明的方式将JSON模式定义附加到它。在这种情况下,您可以选择下面的选项之一来指定JSON布局配置

    手动配置自动映射配置附加元类型类

    我将向您展示如何在每种方法上配置下面的POCO实体类

    清单16.1密封的poco实体类

    隐藏,复制Codepublic sealed class EmployeeRec
    {
    public int Id { get; set; }
    public string Name { get; set; }
    }

    16.1手动配置

    从头定义一个全新的配置对象,并将所有必要的JSON字段添加到ChoJSONConfiguration中。JSONRecordFieldConfigurations集合属性。此选项为您控制JSON解析的配置提供了更大的灵活性。但缺点是,如果JSON文件布局很大,就有可能出错,而且很难管理它们,

    清单16.1.1 手动配置

    隐藏,复制CodeChoJSONRecordConfiguration config = new ChoJSONRecordConfiguration();
    config.ThrowAndStopOnMissingField = true;
    config.JSONRecordFieldConfigurations.Add(new ChoJSONRecordFieldConfiguration(“Id”));
    config.JSONRecordFieldConfigurations.Add(new ChoJSONRecordFieldConfiguration(“Name”));

    16.2,汽车Map 配置

    这是另一种自动映射poco&entity类的JSON列的方法,而且这种方法的错误少得多。

    首先为EmployeeRec POCO实体类定义一个架构类,如下所示

    清单16.2.1自动映射类

    隐藏,复制Codepublic class EmployeeRecMap
    {
    [ChoJSONRecordField]
    public int Id { get; set; }

    [ChoJSONRecordField]
    public string Name { get; set; } 
    

    }

    然后您可以使用ChoJSONRecordConfiguration.MapRecordFields 方法来使用它自动映射JSON列

    清单16.2.2使用自动映射配置

    隐藏,复制CodeChoJSONRecordConfiguration config = new ChoJSONRecordConfiguration();
    config.MapRecordFields();

    EmployeeRec rec1 = new EmployeeRec();
    rec1.Id = 2;
    rec1.Name = “Jason”;

    foreach (var e in new ChoJSONWriter(“emp.json”, config))
    w.Write(rec1);

    16.3,附加MetadataType类

    这是为POCO实体对象附加元类型类的另一种方法。前面的方法只关心JSON列的自动映射。其他配置属性,如属性转换器、解析器参数、默认/回退值等,不被考虑。

    这个模型通过定义元类型类和声明式地指定JSON配置参数来解释所有的事情。当您的POCO实体是密封的而不是部分类时,这是有用的。同时,它也是配置POCO实体的JSON解析的一种有效且较少出错的方法。

    清单16.3.1定义元类型类

    隐藏,收缩,复制Code[ChoJSONRecordObject]
    public class EmployeeRecMeta : IChoNotifyRecordWrite, IChoValidatable
    {
    [ChoJSONRecordField]
    [ChoTypeConverter(typeof(IntConverter))]
    [Range(1, 1, ErrorMessage = “Id must be > 0.”)]
    public int Id { get; set; }

    [ChoJSONRecordField]
    [StringLength(1)]
    [DefaultValue("ZZZ")]
    [ChoFallbackValue("XXX")]
    public string Name { get; set; }
    
    public bool AfterRecordWrite(object target, int index, object source)
    {
        throw new NotImplementedException();
    }
    
    public bool BeforeRecordWrite(object target, int index, ref object source)
    {
        throw new NotImplementedException();
    }
    
    public bool RecordWriteError(object target, int index, object source, Exception ex)
    {
        throw new NotImplementedException();
    }
    
    public bool TryValidate(object target, ICollection<ValidationResult> validationResults)
    {
        return true;
    }
    
    public bool TryValidateFor(object target, string memberName, ICollection<ValidationResult> validationResults)
    {
        return true;
    }
    

    }

    清单16.3.2 Attaching MetadataType类

    隐藏,复制Code//Attach metadata
    ChoMetadataObjectCache.Default.Attach(new EmployeeRecMeta());

    using (var tx = File.OpenWrite(“emp.json”))
    {
    using (var parser = new ChoJSONWriter(tx))
    {
    parser.Write(objs);
    }
    }

    1. ToTextAll辅助方法

    这是一个漂亮的助手方法,用于从对象列表生成JSON格式的输出。它帮助您运行和使用不同的选项,以便在测试环境中快速查看JSON输出。

    隐藏,复制Codestatic void ToTextTest()
    {
    List objs = new List();
    EmployeeRec rec1 = new EmployeeRec();
    rec1.Id = 10;
    rec1.Name = “Mark”;
    objs.Add(rec1);

    EmployeeRec rec2 = new EmployeeRec();
    rec2.Id = 200;
    rec2.Name = "Lou";
    objs.Add(rec2);
    
    Console.WriteLine(ChoJSONWriter.ToTextAll(objs));
    

    }

    17一个。ToText 辅助方法

    这是一个漂亮的助手方法,用于从对象生成JSON格式的输出。它帮助您运行和使用不同的选项,以便在测试环境中快速查看JSON输出。

    隐藏,复制Codestatic void ToTextTest()
    {
    EmployeeRec rec1 = new EmployeeRec();
    rec1.Id = 10;
    rec1.Name = “Mark”;
    objs.Add(rec1);

    Console.WriteLine(ChoJSONWriter.ToText(rec1));
    

    }

    1. 写作DataReader 辅助方法

    这个助手方法允许您从ADO创建JSON文件/流。净DataReader。

    隐藏,复制Codestatic void WriteDataReaderTest()
    {
    SqlConnection conn = new SqlConnection(connString);
    conn.Open();
    SqlCommand cmd = new SqlCommand(“SELECT * FROM Members”, conn);
    IDataReader dr = cmd.ExecuteReader();

    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json))
    {
        parser.Write(dr);
    }
    Console.WriteLine(json.ToString());
    

    }

    1. 编写DataTable辅助方法

    这个助手方法允许您从ADO创建JSON文件/流。净数据表。

    隐藏,复制Codestatic void WriteDataTableTest()
    {
    string connString = @“Data Source=(localdb)\v11.0;Initial Catalog=TestDb;Integrated Security=True”;

    SqlConnection conn = new SqlConnection(connString);
    conn.Open();
    SqlCommand cmd = new SqlCommand("SELECT * FROM Members", conn);
    SqlDataAdapter da = new SqlDataAdapter(cmd);
    DataTable dt = new DataTable();
    da.Fill(dt);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        )
    {
        parser.Write(dt);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    20.高级的主题

    重写转换器的格式规格

    Cinchoo ETL自动解析并将每个JSON列值无缝地转换为对应的JSON列的底层数据类型。大多数基本的。net类型都是自动处理的完成任何需要的设置。

    这是通过ETL系统中的两个关键设置实现的

    ChoJSONRecordConfiguration。CultureInfo——表示关于特定区域性的信息,包括区域性的名称、编写系统和使用的日历,以及对特定区域性对象的访问,这些对象为常见操作提供信息,比如格式化日期和对字符串排序。默认设置是“en - us”。ChoTypeConverterFormatSpec -它是一个全局格式说明符类,包含所有内在的。net类型格式规范。

    在本节中,我将讨论根据解析需要为每个. net内在数据类型更改默认格式规范。

    ChoTypeConverterFormatSpec是单例类,实例通过“instance”静态成员公开。它是线程本地的,这意味着在每个线程上将保留单独的实例副本。

    除了布尔型、枚举型、数据时间型之外,每个内在类型都有两组格式规范成员,一组用于加载,另一组用于写入值。这些类型只有一个用于加载和写入操作的成员。

    通过ChoTypeConverterFormatSpec指定每个内部数据类型格式规范将影响整个系统。ie。setting ChoTypeConverterFormatSpec。IntNumberStyle = NumberStyles。allow圆括号,将影响JSON对象的所有整数成员以允许圆括号。如果您想要重写此行为并控制特定的JSON数据成员来处理它自己的惟一解析JSON值的全局系统范围设置,可以通过在JSON字段成员级别指定TypeConverter来完成。更多信息请参阅13.4节。

    Listing 20.1.1 ChoTypeConverterFormatSpec 成员

    隐藏,收缩,复制Codepublic class ChoTypeConverterFormatSpec
    {
    public static readonly ThreadLocal Instance = new ThreadLocal(() => new ChoTypeConverterFormatSpec());

    public string DateTimeFormat { get; set; }
    public ChoBooleanFormatSpec BooleanFormat { get; set; }
    public ChoEnumFormatSpec EnumFormat { get; set; }
    
    public NumberStyles? CurrencyNumberStyle { get; set; }
    public string CurrencyFormat { get; set; }
    
    public NumberStyles? BigIntegerNumberStyle { get; set; }
    public string BigIntegerFormat { get; set; }
    
    public NumberStyles? ByteNumberStyle { get; set; }
    public string ByteFormat { get; set; }
    
    public NumberStyles? SByteNumberStyle { get; set; }
    public string SByteFormat { get; set; }
    
    public NumberStyles? DecimalNumberStyle { get; set; }
    public string DecimalFormat { get; set; }
    
    public NumberStyles? DoubleNumberStyle { get; set; }
    public string DoubleFormat { get; set; }
    
    public NumberStyles? FloatNumberStyle { get; set; }
    public string FloatFormat { get; set; }
    
    public string IntFormat { get; set; }
    public NumberStyles? IntNumberStyle { get; set; }
    
    public string UIntFormat { get; set; }
    public NumberStyles? UIntNumberStyle { get; set; }
    
    public NumberStyles? LongNumberStyle { get; set; }
    public string LongFormat { get; set; }
    
    public NumberStyles? ULongNumberStyle { get; set; }
    public string ULongFormat { get; set; }
    
    public NumberStyles? ShortNumberStyle { get; set; }
    public string ShortFormat { get; set; }
    
    public NumberStyles? UShortNumberStyle { get; set; }
    public string UShortFormat { get; set; }
    

    }

    下面的示例展示了如何使用JSONWriter加载具有“se-SE”(瑞典)区域性特定数据的JSON数据流。此外,输入提要带有包含括号的“EmployeeNo”值。为了使加载成功,我们必须设置ChoTypeConverterFormatSpec。IntNumberStyle NumberStyles.AllowParenthesis。

    在代码中使用ChoTypeConverterFormatSpec

    隐藏,收缩,复制Codestatic void FormatSpecDynamicTest()
    {
    ChoTypeConverterFormatSpec.Instance.DateTimeFormat = “d”;
    ChoTypeConverterFormatSpec.Instance.BooleanFormat = ChoBooleanFormatSpec.YOrN;

    List<ExpandoObject> objs = new List<ExpandoObject>();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = "Mark";
    rec1.JoinedDate = new DateTime(2001, 2, 2);
    rec1.IsActive = true;
    objs.Add(rec1);
    
    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    rec2.JoinedDate = new DateTime(1990, 10, 23);
    rec2.IsActive = false;
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    20.2,货币支持

    Cinchoo ETL提供ChoCurrency对象来读写JSON文件中的货币值。ChoCurrency是一个包装类,用于保存十进制类型的货币值,并支持在JSON加载期间以文本格式序列化它们。

    列表20.2.1在动态模型中使用货币成员

    隐藏,收缩,复制Codestatic void CurrencyDynamicTest()
    {
    ChoTypeConverterFormatSpec.Instance.CurrencyFormat = “C2”;

    List<ExpandoObject> objs = new List<ExpandoObject>();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = "Mark";
    rec1.JoinedDate = new DateTime(2001, 2, 2);
    rec1.IsActive = true;
    rec1.Salary = new ChoCurrency(100000);
    objs.Add(rec1);
    
    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    rec2.JoinedDate = new DateTime(1990, 10, 23);
    rec2.IsActive = false;
    rec2.Salary = new ChoCurrency(150000);
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    上面的示例展示了如何使用动态对象模型输出货币值。由于货币输出将具有千个逗号分隔符,这将无法生成JSON文件。为了克服这个问题,我们指定写入器引用所有字段。

    PS:货币值的格式是JSONWriter通过ChoRecordConfiguration计算出来的。文化和ChoTypeConverterFormatSpec.CurrencyFormat。

    下面的示例展示了如何在POCO实体类中使用ChoCurrency JSON字段。

    在POCO模型中使用货币成员

    隐藏,收缩,复制Codepublic class EmployeeRecWithCurrency
    {
    public int Id { get; set; }
    public string Name { get; set; }
    public ChoCurrency Salary { get; set; }
    }

    static void CurrencyPOCOTest()
    {
    List objs = new List();
    EmployeeRecWithCurrency rec1 = new EmployeeRecWithCurrency();
    rec1.Id = 10;
    rec1.Name = “Mark”;
    rec1.Salary = new ChoCurrency(100000);
    objs.Add(rec1);

    EmployeeRecWithCurrency rec2 = new EmployeeRecWithCurrency();
    rec2.Id = 200;
    rec2.Name = "Lou";
    rec2.Salary = new ChoCurrency(150000);
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter<EmployeeRecWithCurrency>(json)
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    20.3, Enum 支持

    Cinchoo ETL隐式处理JSON文件中枚举列值的解析/写入。如果您想精确地控制这些值的解析,您可以通过ChoTypeConverterFormatSpec.EnumFormat全局指定它们。缺省为ChoEnumFormatSpec.Value

    供您参考,更改此值将影响整个系统。

    有3种可能的值可以使用

    ChoEnumFormatSpec。Value—枚举值用于解析。ChoEnumFormatSpec。Name—用于解析的枚举键名。ChoEnumFormatSpec。Description——如果每个枚举键都用DescriptionAttribute修饰,那么它的值将用于解析。

    清单20.3.1在解析期间指定枚举格式规范

    隐藏,收缩,复制Codepublic enum EmployeeType
    {
    [Description(“Full Time Employee”)]
    Permanent = 0,
    [Description(“Temporary Employee”)]
    Temporary = 1,
    [Description(“Contract Employee”)]
    Contract = 2
    }

    static void EnumTest()
    {
    ChoTypeConverterFormatSpec.Instance.EnumFormat = ChoEnumFormatSpec.Description;

    List<ExpandoObject> objs = new List<ExpandoObject>();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = "Mark";
    rec1.JoinedDate = new DateTime(2001, 2, 2);
    rec1.IsActive = true;
    rec1.Salary = new ChoCurrency(100000);
    rec1.Status = EmployeeType.Permanent;
    objs.Add(rec1);
    
    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    rec2.JoinedDate = new DateTime(1990, 10, 23);
    rec2.IsActive = false;
    rec2.Salary = new ChoCurrency(150000);
    rec2.Status = EmployeeType.Contract;
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    20.4,布尔的支持

    Cinchoo ETL隐式处理JSON文件中布尔JSON列值的解析/写入。如果你想更好地控制解析这些值,你可以通过ChoTypeConverterFormatSpec.BooleanFormat全局指定它们,默认值是ChoBooleanFormatSpec.ZeroOrOne

    供您参考,更改此值将影响整个系统。

    有4个可能的值可以使用

    ChoBooleanFormatSpec。0或1 - ‘0’表示false。’ 1 ',真的。ChoBooleanFormatSpec。YOrN - 'Y’表示真,'N’表示假。ChoBooleanFormatSpec。真或假——真用True表示,假用False表示。ChoBooleanFormatSpec。YesOrNo——用Yes表示正确,用No表示错误。

    清单20.4.1在解析期间指定布尔格式规范

    隐藏,收缩,复制Codestatic void BoolTest()
    {
    ChoTypeConverterFormatSpec.Instance.BooleanFormat = ChoBooleanFormatSpec.YOrN;

    List<ExpandoObject> objs = new List<ExpandoObject>();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = "Mark";
    rec1.JoinedDate = new DateTime(2001, 2, 2);
    rec1.IsActive = true;
    rec1.Salary = new ChoCurrency(100000);
    rec1.Status = EmployeeType.Permanent;
    objs.Add(rec1);
    
    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    rec2.JoinedDate = new DateTime(1990, 10, 23);
    rec2.IsActive = false;
    rec2.Salary = new ChoCurrency(150000);
    rec2.Status = EmployeeType.Contract;
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    20.5,DateTime支持

    Cinchoo ETL隐式处理使用系统区域性或自定义集区域性从JSON文件解析/写入datetime JSON列值。如果您想精确地控制这些值的解析,可以将它们指定为gl显然,via chotypeconverterformat . datetimeformat .缺省值是’d’。

    供您参考,更改此值将影响整个系统。

    您可以使用任何有效的标准或自定义日期时间。NET格式规范来解析文件中的日期时间JSON值。

    清单20.5.1在解析期间指定日期时间格式规范

    隐藏,收缩,复制Codestatic void DateTimeDynamicTest()
    {
    ChoTypeConverterFormatSpec.Instance.DateTimeFormat = “MMM dd, yyyy”;

    List<ExpandoObject> objs = new List<ExpandoObject>();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = "Mark";
    rec1.JoinedDate = new DateTime(2001, 2, 2);
    rec1.IsActive = true;
    rec1.Salary = new ChoCurrency(100000);
    objs.Add(rec1);
    
    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    rec2.JoinedDate = new DateTime(1990, 10, 23);
    rec2.IsActive = false;
    rec2.Salary = new ChoCurrency(150000);
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    上面的示例展示了如何为JSON文件生成定制的datetime值。

    注意:由于日期时间值包含JSON分隔符,我们要求作者引用所有字段。

    1. 流利的API

    JSONWriter通过fluent API方法公开很少使用的配置参数。这将使生成JSON文件的编程变得更快。

    21.1。NullValueHandling

    指定ChoJSONWriter的空值处理选项

    Ignore—在编写JSON时忽略null值

    默认值——在编写JSON时包含空值

    21.2只格式化

    指定ChoJSONWriter的格式设置选项

    None -不应用任何特殊格式。这是默认值。

    Intented—导致子对象缩进。

    21.3, WithFields

    这个API方法指定编写JSON文件时要考虑的JSON字段列表。其他字段将被丢弃。字段名不区分大小写。

    隐藏,收缩,复制Codestatic void QuickDynamicTest()
    {
    List objs = new List();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = “Mark”;
    rec1.JoinedDate = new DateTime(2001, 2, 2);
    rec1.IsActive = true;
    rec1.Salary = new ChoCurrency(100000);
    objs.Add(rec1);

    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    rec2.JoinedDate = new DateTime(1990, 10, 23);
    rec2.IsActive = false;
    rec2.Salary = new ChoCurrency(150000);
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        .WithFields("Id", "Name")
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    21.4,WithField

    此API方法用于添加带有特定日期类型、引号标志和/或引号字符的JSON列。通过使用适当的数据类型指定每个JSON列,此方法在动态对象模型中很有帮助。,

    隐藏,收缩,复制Codestatic void QuickDynamicTest()
    {
    List objs = new List();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = “Mark”;
    rec1.JoinedDate = new DateTime(2001, 2, 2);
    rec1.IsActive = true;
    rec1.Salary = new ChoCurrency(100000);
    objs.Add(rec1);

    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    rec2.JoinedDate = new DateTime(1990, 10, 23);
    rec2.IsActive = false;
    rec2.Salary = new ChoCurrency(150000);
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        .WithField("Id", typeof(int))
        .WithField("Name"))
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    21.5只IgnoreFieldValueMode

    为ChoJSONWriter指定忽略字段值

    None - Ignore字段值被关闭。这是默认值。

    DbNull值将被忽略。

    Empty -空文本值将被忽略。

    空格-空格文本将被忽略。

    21.6,ColumnCountStrict

    这个API方法用于设置JSONWriter,以便在编写JSON文件之前对列计数进行检查。

    隐藏,收缩,复制Codestatic void ColumnCountTest()
    {
    List objs = new List();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = “Mark”;
    rec1.JoinedDate = new DateTime(2001, 2, 2);
    rec1.IsActive = true;
    rec1.Salary = new ChoCurrency(100000);
    objs.Add(rec1);

    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    rec2.JoinedDate = new DateTime(1990, 10, 23);
    rec2.IsActive = false;
    rec2.Salary = new ChoCurrency(150000);
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        .ColumnCountStrict()
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    21.7。配置

    此API方法用于配置所有未通过fluent API公开的配置参数。

    隐藏,复制Codestatic void ConfigureTest()
    {
    List objs = new List();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = “Mark”;
    objs.Add(rec1);

    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        .Configure(c => c.ErrorMode = ChoErrorMode.ThrowAndStop)
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    21.8。设置

    此API方法用于通过fluent API设置写入器的参数/事件。

    隐藏,复制Codestatic void SetupTest()
    {
    List objs = new List();
    dynamic rec1 = new ExpandoObject();
    rec1.Id = 10;
    rec1.Name = “Mark”;
    objs.Add(rec1);

    dynamic rec2 = new ExpandoObject();
    rec2.Id = 200;
    rec2.Name = "Lou";
    objs.Add(rec2);
    
    StringBuilder json = new StringBuilder();
    using (var parser = new ChoJSONWriter(json)
        .Setup(r => r.BeforeRecordWrite += (o, e) =>
        {
        })
        )
    {
        parser.Write(objs);
    }
    
    Console.WriteLine(json.ToString());
    

    }

    1. 常见问题解答

    22.1。如何序列化一个对象?

    此示例将对象序列化为JSON

    隐藏,复制Codestring json = ChoJSONWriter.Serialize(new Account
    {
    Email = “james@example.com”,
    Active = true,
    Roles = new List()
    {
    “DEV”,
    “OPS”
    }
    });

    22.2。如何序列化对象的集合?

    此示例将对象集合序列化为JSON

    隐藏,复制Codestring json = ChoJSONWriter.SerializeAll(new Account[] {
    new Account
    {
    Email = “james@example.com”,
    Active = true,
    Roles = new List()
    {
    “DEV”,
    “OPS”
    }
    }
    }
    );

    22.3。如何序列化动态对象?

    这个示例将动态对象序列化为JSON

    隐藏,复制Codedynamic obj = new ExpandoObject();
    obj.Email = “james@example.com”;
    obj.Active = true;
    obj.Roles = new List()
    {
    “DEV”,
    “OPS”
    };

    string json = ChoJSONWriter.Serialize(obj);

    Console.WriteLine(json);

    22.4。如何序列化匿名对象?

    这个示例将匿名对象序列化为JSON

    隐藏,复制Codestring json = ChoJSONWriter.Serialize(new
    {
    Email = “james@example.com”,
    Active = true,
    Roles = new List()
    {
    “DEV”,
    “OPS”
    }
    });

    Console.WriteLine(json);

    22.5。如何序列化集合?

    这个示例将集合序列化为JSON

    隐藏,复制Codestring json = ChoJSONWriter.SerializeAll(new int[] { 1, 2, 3 });

    Console.WriteLine(json);

    22.6。如何序列化字典?

    这个示例将字典序列化为JSON

    隐藏,复制Codestring json = ChoJSONWriter.SerializeAll(new Dictionary<string, int>[] {
    new Dictionary<string, int>()
    {
    [“key1”] = 1,
    [“key2”] = 2
    }
    });

    Console.WriteLine(json);

    22.7。如何序列化数据表?

    这个示例将datatable序列化为JSON

    隐藏,复制CodeStringBuilder sb = new StringBuilder();
    string connectionstring = @“Data Source=(localdb)\MSSQLLocalDB;Initial Catalog=Northwind;Integrated Security=True”;
    using (var conn = new SqlConnection(connectionstring))
    {
    conn.Open();
    var comm = new SqlCommand(“SELECT TOP 2 * FROM Customers”, conn);
    SqlDataAdapter adap = new SqlDataAdapter(comm);

    DataTable dt = new DataTable("Customer");
    adap.Fill(dt);
    
    using (var parser = new ChoJSONWriter(sb)
        .Configure(c => c.IgnoreRootName = true)
        )
        parser.Write(dt);
    

    }

    Console.WriteLine(sb.ToString());

    22.8。如何序列化JSON到一个文件?

    这个示例将JSON序列化为一个文件。

    隐藏,复制Code// serialize JSON to a string and then write string to a file
    File.WriteAllText(@“c:\emp.json”, ChoJSONWriter.Serialize(employee));

    下面的示例展示了如何直接写入文件

    隐藏,复制Codeusing (StreamWriter file = File.CreateText(@“c:\emp.json”))
    {
    using (var r = new ChoJSONWriter(file))
    r.Write(employee);
    }

    22.9。如何序列化未缩进的JSON?

    这个示例将一个对象序列化为JSON,没有格式化或缩进空格。

    隐藏,复制Codestring json = ChoJSONWriter.SerializeAll(new int[] { 1, 2, 3 },
    new ChoJSONRecordConfiguration().Configure(c => c.Formatting = Formatting.None));

    Console.WriteLine(json);

    22.10。如何序列化条件属性?

    此示例使用条件属性从序列化中排除属性。

    隐藏,收缩,复制Codepublic class Employee
    {
    public string Name { get; set; }
    public Employee Manager { get; set; }

    public bool ShouldSerializeManager()
    {
        // don't serialize the Manager property if an employee is their own manager
        return (Manager != this);
    }
    

    }

    public static void ConditionalPropertySerialize()
    {
    Employee joe = new Employee();
    joe.Name = “Joe Employee”;
    Employee mike = new Employee();
    mike.Name = “Mike Manager”;

    joe.Manager = mike;
    
    // mike is his own manager
    // ShouldSerialize will skip this property
    mike.Manager = mike;
    
    string json = ChoJSONWriter.SerializeAll(new[] { joe, mike }, new ChoJSONRecordConfiguration().Configure(c => c.UseJSONSerialization = true));
    
    Console.WriteLine(json);
    

    }

    22.11。如何序列化的日期时间在自定义日期格式?

    此示例使用DateFormatString设置来控制如何序列化datetime和datetimeoffset。

    隐藏,复制CodeIList dateList = new List
    {
    new DateTime(2009, 12, 7, 23, 10, 0, DateTimeKind.Utc),
    new DateTime(2010, 1, 1, 9, 0, 0, DateTimeKind.Utc),
    new DateTime(2010, 2, 10, 10, 0, 0, DateTimeKind.Utc)
    };

    string json = ChoJSONWriter.SerializeAll(dateList, new JsonSerializerSettings
    {
    DateFormatString = “d MMMM, yyyy”,
    Formatting = Formatting.Indented
    });

    Console.WriteLine(json);

    如何从Json序列化中排除属性?

    这些示例展示了如何从JSON序列化中排除属性

    Sample1:使用ChoIgnoreMemberAttribute

    隐藏,复制Codepublic class Account
    {
    [ChoIgnoreMember]
    public string Email { get; set; }
    public bool Active { get; set; }
    public DateTime CreatedDate { get; set; }
    public IList Roles { get; set; }
    }

    static void ExcludePropertyTest()
    {
    string json = ChoJSONWriter.Serialize(new Account
    {
    Email = “james@example.com”,
    Active = true,
    Roles = new List()
    {
    “DEV”,
    “OPS”
    }

    });
    
    Console.WriteLine(json);
    

    }

    Sample2:使用JsonIgnoreAttribute

    隐藏,复制Codepublic class Account
    {
    [JsonIgnore]
    public string Email { get; set; }
    public bool Active { get; set; }
    public DateTime CreatedDate { get; set; }
    public IList Roles { get; set; }
    }

    static void ExcludePropertyTest()
    {
    string json = ChoJSONWriter.Serialize(new Account
    {
    Email = “james@example.com”,
    Active = true,
    Roles = new List()
    {
    “DEV”,
    “OPS”
    }

    });
    
    Console.WriteLine(json);
    

    }

    Sample3:在ChoJSONConfiguration上使用IgnoreField

    隐藏,复制Codepublic class Account
    {
    public string Email { get; set; }
    public bool Active { get; set; }
    public DateTime CreatedDate { get; set; }
    public IList Roles { get; set; }
    }

    static void ExcludePropertyTest()
    {
    string json = ChoJSONWriter.Serialize(new Account
    {
    Email = “james@example.com”,
    Active = true,
    Roles = new List()
    {
    “DEV”,
    “OPS”
    }

    }, new ChoJSONRecordConfiguration<Account>().Ignore(f => f.Email));
    
    Console.WriteLine(json);
    

    }

    Sample4:在ChoJSONWriter上使用IgnoreField

    隐藏,收缩,复制Codepublic class Account
    {
    public string Email { get; set; }
    public bool Active { get; set; }
    public DateTime CreatedDate { get; set; }
    public IList Roles { get; set; }
    }

    static void ExcludePropertyTest()
    {
    StringBuilder json = new StringBuilder();
    using (var w = new ChoJSONWriter(json)
    .IgnoreField(f => f.Email)
    )
    {
    w.Write(new Account
    {
    Email = “james@example.com”,
    Active = true,
    Roles = new List()
    {
    “DEV”,
    “OPS”
    }

        });
    }
    
    Console.WriteLine(json);
    

    }

    22.13.如何将Xml转换成JSON?

    这个示例展示了如何将Xml文件转换为JSON。

    隐藏,复制Codestring xml = @"<Employees xmlns="“http://company.com/schemas”">

    name1
    surname1


    name2
    surname2


    name3
    surname3

    ";

    StringBuilder json = new StringBuilder();
    using (var r = ChoXmlReader.LoadText(xml))
    {
    using (var w = new ChoJSONWriter(json))
    w.Write®;
    }

    Console.WriteLine(json.ToString());

    输出:

    隐藏,复制Code[
    {
    “FirstName”: “name1”,
    “LastName”: “surname1”
    },
    {
    “FirstName”: “name2”,
    “LastName”: “surname2”
    },
    {
    “FirstName”: “name3”,
    “LastName”: “surname3”
    }
    ]

    22.14.如何将CSV转换成JSON?

    这个示例展示了如何将CSV文件转换为JSON。

    隐藏,复制Codestring csv = @“Id, First Name
    1, Tom
    2, Mark”;

    StringBuilder json = new StringBuilder();
    using (var r = ChoCSVReader.LoadText(csv)
    .WithFirstLineHeader()
    .WithMaxScanRows(2)
    )
    {
    using (var w = new ChoJSONWriter(json)
    //.Configure(c => c.Formatting = Formatting.None)
    //.SupportMultipleContent()
    //.SingleElement()
    )
    {
    w.Write(r.Take(2));
    }
    }

    Console.WriteLine(json.ToString());

    ,

    本文转载于:http://www.diyabc.com/frontweb/news127.html

    展开全文
  • 用于处理OpenFDA FAERS DB的OpenTargets ETL管道。 开放式FDA药物不良事件API返回从FDA不良事件报告系统(FAERS)收集的数据,该数据库包含有关提交给FDA的不良事件和用药错误报告的信息。 管道支持可以在配置文件...
  • Spark有统一个外部数据源API,可以轻松实现ETL功能。 pom.xml &lt;project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:...

    Spark有统一个外部数据源API,可以轻松实现ETL功能。

    pom.xml

    <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
      <modelVersion>4.0.0</modelVersion>
      <groupId>com.sid.com</groupId>
      <artifactId>sparksqltrain</artifactId>
      <version>1.0-SNAPSHOT</version>
      <inceptionYear>2008</inceptionYear>
      <properties>
        <scala.version>2.11.8</scala.version>
        <spark.version>2.2.0</spark.version>
      </properties>
    
      <repositories>
        <repository>
          <id>scala-tools.org</id>
          <name>Scala-Tools Maven2 Repository</name>
          <url>http://scala-tools.org/repo-releases</url>
        </repository>
      </repositories>
    
      <pluginRepositories>
        <pluginRepository>
          <id>scala-tools.org</id>
          <name>Scala-Tools Maven2 Repository</name>
          <url>http://scala-tools.org/repo-releases</url>
        </pluginRepository>
      </pluginRepositories>
    
      <dependencies>
        <!-- scala依赖 -->
        <dependency>
          <groupId>org.scala-lang</groupId>
          <artifactId>scala-library</artifactId>
          <version>${scala.version}</version>
        </dependency>
        <!-- spark依赖 -->
        <dependency>
          <groupId>org.apache.spark</groupId>
          <artifactId>spark-sql_2.11</artifactId>
          <version>${spark.version}</version>
        </dependency>
        <!-- hivecontext要用这个依赖-->
        <dependency>
          <groupId>org.apache.spark</groupId>
          <artifactId>spark-hive_2.11</artifactId>
          <version>${spark.version}</version>
        </dependency>
    
        <dependency>
          <groupId>org.spark-project.hive</groupId>
          <artifactId>hive-jdbc</artifactId>
          <version>1.2.1.spark2</version>
        </dependency>
    
      </dependencies>
    
      <build>
        <sourceDirectory>src/main/scala</sourceDirectory>
        <testSourceDirectory>src/test/scala</testSourceDirectory>
        <plugins>
          <plugin>
            <groupId>org.scala-tools</groupId>
            <artifactId>maven-scala-plugin</artifactId>
            <executions>
              <execution>
                <goals>
                  <goal>compile</goal>
                  <goal>testCompile</goal>
                </goals>
              </execution>
            </executions>
            <configuration>
              <scalaVersion>${scala.version}</scalaVersion>
              <args>
                <arg>-target:jvm-1.5</arg>
              </args>
            </configuration>
          </plugin>
          <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-eclipse-plugin</artifactId>
            <configuration>
              <downloadSources>true</downloadSources>
              <buildcommands>
                <buildcommand>ch.epfl.lamp.sdt.core.scalabuilder</buildcommand>
              </buildcommands>
              <additionalProjectnatures>
                <projectnature>ch.epfl.lamp.sdt.core.scalanature</projectnature>
              </additionalProjectnatures>
              <classpathContainers>
                <classpathContainer>org.eclipse.jdt.launching.JRE_CONTAINER</classpathContainer>
                <classpathContainer>ch.epfl.lamp.sdt.launching.SCALA_CONTAINER</classpathContainer>
              </classpathContainers>
            </configuration>
          </plugin>
        </plugins>
      </build>
      <reporting>
        <plugins>
          <plugin>
            <groupId>org.scala-tools</groupId>
            <artifactId>maven-scala-plugin</artifactId>
            <configuration>
              <scalaVersion>${scala.version}</scalaVersion>
            </configuration>
          </plugin>
        </plugins>
      </reporting>
    </project>
    
    ParquetApp.scala代码
    package com.sid.com
    
    import org.apache.spark.sql.SparkSession
    
    /**
      * Spark 实现ETL功能
      * 读json文件,写成parquet文件
      * */
    object ParquetApp {
      def main(args: Array[String]): Unit = {
        val spark = SparkSession.builder().appName("ParquetApp").master("local[2]").getOrCreate()
    
        //不指定format会默认按照parquet处理
        //读json
       var peopleDFReadJson = spark.read.format("json").load("file:///G:/desktop/people.json")
        peopleDFReadJson.printSchema()
        peopleDFReadJson.show()
        //写成parquet
        peopleDFReadJson.write.parquet("file:///G:/desktop/people")
    
        //读parquet看是否正确
        val peopleDFReadParquet = spark.read.format("parquet").load("file:///G:/desktop/people")
        peopleDFReadParquet.printSchema()
        peopleDFReadParquet.show()
      }
    
    }
    

     

    展开全文
  • 如果生成的日志数据是Avro格式,可直接...但是我们一般都是日志数据不是Avro,大部分是Json数据。因此,本篇主要讲如何将Json通过Morphline流式转储为Parquet数据。文章中只是简单的例子,在实际生产环境中,我们...
    如果生成的日志数据是Avro格式,可直接采用上一篇的方式(https://blog.csdn.net/qq_29829081/article/details/80518671),将Avro数据转储为Parquet。但是我们一般都是日志数据不是Avro,大部分是Json数据。因此,本篇主要讲如何将Json通过Morphline流式转储为Parquet数据。文章中只是简单的例子,在实际生产环境中,我们的Json数据非常复杂,但是也可以采用Morphline进行转储,可以采用通用的方式进行处理,下一节再详述。

    本节主要讲述如何借助于flume的Morphline Interceptor,将json数据线临时转成avro,再通过kite dataset sink最终将数据转成parquet格式进行存储。其实最关键的就是Flume的配置,Morphline命令行的组合。

    1 Flume配置:

    (1) nginx端flume配置

    # Name the components on this agent
    a1.sources = r
    a1.sinks = k_kafka
    a1.channels = c_mem
    
    # Channelsinfo
    a1.channels.c_mem.type = memory
    a1.channels.c_mem.capacity = 2000
    a1.channels.c_mem.transactionCapacity = 300
    a1.channels.c_mem.keep-alive = 60
    
    # Sources info
    a1.sources.r.type = exec
    a1.sources.r.shell = /bin/bash -c
    a1.sources.r.command = tail -F /home/litao/litao.json
    a1.sources.r.channels = c_mem
    
    # Sinks info
    a1.sinks.k_kafka.channel  = c_mem
    a1.sinks.k_kafka.type = org.apache.flume.sink.kafka.KafkaSink
    a1.sinks.k_kafka.kafka.bootstrap.servers = kafka1:9093,kafka2:9093,kafka3:9093,kafka4:9093,kafka5:9093,kafka6:9093
    a1.sinks.k_kafka.kafka.topic = test_2018-03-14
    a1.sinks.k_kafka.kafka.flumeBatchSize = 5
    a1.sinks.k_kafka.kafka.producer.acks =1

    (2) kafka端flume配置
    # Name the components on this agent
    a1.channels = c1
    a1.sources = r1
    a1.sinks  = k1
    
    # Channel config
    a1.channels.c1.type = memory
    a1.channels.c1.capacity = 500000
    a1.channels.c1.transactionCapacity =100000
    a1.channels.c1.keep-alive = 50
    
    # Sources info
    a1.sources.r1.type = com.bigo.flume.source.kafka.KafkaSource
    a1.sources.r1.channels = c1
    a1.sources.r1.kafka.bootstrap.servers = kafka1:9093,kafka2:9093,kafka3:9093,kafka4:9093,kafka5:9093,kafka6:9093
    a1.sources.r1.kafka.topics = test_2018-03-14
    a1.sources.r1.kafka.consumer.group.id = test_2018-03-14.conf_flume_group
    a1.sources.r1.kafka.consumer.timeout.ms = 100
    a1.sources.r1.batchSize = 2000
    
    # Config Interceptors
    a1.sources.r1.interceptors=i1 morphline
    
    # Inject the Schema into the header so the AvroEventSerializer can pick it up
    a1.sources.r1.interceptors.i1.type = static
    a1.sources.r1.interceptors.i1.key = flume.avro.schema.url
    #a1.sources.r1.interceptors.i1.value = file:/home/litao/litao.avsc
    a1.sources.r1.interceptors.i1.value=hdfs://bigocluster/user/litao/litao.avsc
    
    # Morphline interceptor config
    a1.sources.r1.interceptors.morphline.type = org.apache.flume.sink.solr.morphline.MorphlineInterceptor$Builder
    a1.sources.r1.interceptors.morphline.morphlineFile = /etc/flume/conf/a1/morphline.conf
    a1.sources.r1.interceptors.morphline.morphlineId = convertJsonToAvro
    
    # Sink config
    a1.sinks.k1.type  = org.apache.flume.sink.kite.DatasetSink
    a1.sinks.k1.channel  = c1
    a1.sinks.k1.kite.dataset.uri  = dataset:hdfs://bigocluster/flume/hellotalk/parquet
    a1.sinks.k1.kite.batchSize = 100
    a1.sinks.k1.kite.rollInterval = 30

    2 morphlines配置:
                        morphlines: [
      {
        id: convertJsonToAvro
        importCommands: [ "org.kitesdk.**" ]
        commands: [
          # read the JSON blob
          { readJson: {} }
          # extract JSON objects into fields
          { extractJsonPaths {
            flatten: true
            paths: {
              name: /name
              age: /age
            }
          } }
          # add a creation timestamp to the record
          #{ addCurrentTime {
          #  field: timestamp
          #  preserveExisting: true
          #} }
          # convert the extracted fields to an avro object
          # described by the schema in this field
          { toAvro {
            schemaFile: /home/litao/litao.avsc
          } }
          # serialize the object as avro
          { writeAvroToByteArray: {
            format: containerlessBinary
          } }
        ]
      }
    ]
    3 依赖的jar包:
    config-1.3.1.jar
    metrics-healthchecks-3.0.2.jar
    kite-morphlines-core-1.1.0.jar
    kite-morphlines-json-1.1.0.jar
    kite-morphlines-avro-1.1.0.jar

    展开全文
  • ETL-Kettle读取Json数据输出到Excel

    千次阅读 2019-08-26 14:19:03
    json元数据: { “status”: “ok”, “response”: { “submissions”: [ { “id”: “59434767”, “timestamp”: “2011-11-21 09:21:53”, “user_agent”: “Mozilla/5.0 (Windows NT 6.1; WOW64; rv:8.0) ...

    json元数据:
    {
    “status”: “ok”,
    “response”: {
    “submissions”: [
    {
    “id”: “59434767”,
    “timestamp”: “2011-11-21 09:21:53”,
    “user_agent”: “Mozilla/5.0 (Windows NT 6.1; WOW64; rv:8.0) Gecko/20100101 Firefox/8.0”,
    “remote_addr”: “192.168.1.1”,
    “payment_status”: “”,
    “data”: [
    {
    “field”: “13776121”,
    “value”: “Baylor Dallas”
    },
    {
    “field”: “13776401”,
    “value”: “CHF”
    },
    {
    “field”: “13777966”,
    “value”: “John Doe”
    },
    {
    “field”: “13780027”,
    “value”: “9999”
    },
    {
    “field”: “13778165”,
    “value”: “None of the above”
    },
    {
    “field”: “13778985”,
    “value”: “Yes”
    },
    {
    “field”: “13778280”,
    “value”: “Yes”
    },
    {
    “field”: “13778424”,
    “value”: “Yes”
    },
    {
    “field”: “13778290”,
    “value”: “Yes”
    },
    {
    “field”: “13778324”,
    “value”: “Yes”
    },
    {
    “field”: “13778864”,
    “value”: “Yes”
    }
    ]
    },
    {
    “id”: “59474875”,
    “timestamp”: “2011-11-21 17:01:22”,
    “user_agent”: “Mozilla/5.0 (Windows NT 6.1; WOW64; rv:8.0) Gecko/20100101 Firefox/8.0”,
    “remote_addr”: “192.168.1.1”,
    “payment_status”: “”,
    “data”: [
    {
    “field”: “13776121”,
    “value”: “Healthsouth,”
    },
    {
    “field”: “13776401”,
    “value”: “Pneumonia”
    },
    {
    “field”: “13777966”,
    “value”: “Jane Doe”
    },
    {
    “field”: “13780027”,
    “value”: “390”
    },
    {
    “field”: “13778165”,
    “value”: “Experienced a fall?”
    },
    {
    “field”: “13861153”,
    “value”: “Yes”
    },
    {
    “field”: “13780018”,
    “value”: “Yes”
    },
    {
    “field”: “13780006”,
    “value”: “No”
    },
    {
    “field”: “13780023”,
    “value”: “Yes”
    },
    {
    “field”: “13780024”,
    “value”: “Yes”
    }
    ]
    }
    ],
    “total”: 2,
    “pages”: 1
    }
    }

    第一步选择:
    新建一个转换,选择JSON输入
    在这里插入图片描述

    第二步编辑这个转换,选择上述json文件的路径,然后点击添加
    在这里插入图片描述
    在这里插入图片描述
    再插入一个JSON输入转换
    在这里插入图片描述

    配置这个json输入
    在这里插入图片描述

    在这里插入图片描述

    选择一个Excel输出
    在这里插入图片描述

    在这里插入图片描述

    在这里插入图片描述

    在这里插入图片描述

    展开全文
  • 一.Json对象与Json字符串的转化 1.jQuery插件支持的转换方式:  $.parseJSON( jsonstr ); //jQuery.parseJSON(jsonstr),可以将json字符串转换成json对象   2.浏览器支持的转换方式(Firefox,chrome,...
  • 主要是先获取到json,然后非常清楚json的结构形式,然后明确自己需要哪些字段。最后根据jsonPath编写出各个解析各个字段获取对应的值得json解析路径。通过这样一个思路就可以利用Kettle零代码快速完成json解析工作。...
  • Kettle作为开源ETL工具,使用较多(因为不花钱)。 最近我个人在使用的时候遇到了需要将hive的数据以Json的格式推动到API接口。调用API使用的是Kettle的组件“rest client”。具体的流程如下: 因为向下游推送...
  • 最近做数据清洗及传输,要求用ETL做调度,所以研究了下Kettle的Json组件,FTP组件以及Java代码组件,这次主要记录下Java代码处理文件的方法,方便以后的使用   先说下处理大概流程: 1、客户端从各系统抽取数据...
  • 数据扁平化处理,将之前一个个嵌套的json存储为一个一维的,规范的表结构作数据准备 3、数据集成 将日志的GPS与之前准备好的字典信息补完整,方便后面做地域的维度分析 集成商圈信息,方便后..
  • 不多说,直接上干货!  这是来自FineBI官网提供的帮助文档 http://help.finebi.com/http://help.finebi.com/doc-view-48.html ...4、ETL处理类型 1、描述 ...
  • 风筝SDK Morplines 从其描述复制而来: Morphlines是一个开源框架,它减少了构建和更改Hadoop ETL处理应用程序所需的时间和精力,该应用程序可将数据提取,转换并加载到Apache Solr,HBase,HDFS,Enterprise ...
  • sparksql处理嵌套json

    千次阅读 2019-04-03 13:42:05
    本文主要讲spark2.0版本以后存在的Sparksql的一些实用的函数,帮助解决复杂嵌套的json数据格式,比如,map和嵌套结构。Spark2.1在spark 的Structured Streaming也可以使用这些功能函数。 下面几个是本文重点要讲的...
  • 风筝SDK Morplines 从其描述复制: Morphlines是一个开源框架,可减少构建和更改Hadoop ETL处理应用程序所需的时间和精力,该应用程序可将数据提取,转换并加载到Apache Solr,HBase,HDFS,Enterprise Data ...
  • 10-每日全量案例实现.avi ├─10-访客分析.avi ├─11-ETL处理-创建hive表接收ETL处理后数据.mp4 ├─11-kettle输出组件之表输出插入更新删除组件.avi ├─11-kylin全量构建与增量构建介绍.avi ├─11-superset ...
  • https://help.pentaho.com/Documentation/8.2/Developer_Center/PDI/Embed https://wiki.pentaho.com/pages/viewpage.action?pageId=13175504 https://jaxenter.com/run-pdi-based-etl-java-154655.html
  • ETL

    2018-01-08 16:48:43
    ... 通常情况下,在BI项目中ETL会花掉整个项目至少1/3的时间,ETL设计的好坏直接关接到BI项目的成败。   ETL的设计分三部分:数据抽取、数据的清洗转换、数据的加载。在设计ETL的时候我们也...
  • 一个ETL转换器,用于处理社交媒体数据并将结果输出到csv文件中。 先决条件 Java 8 Maven 3.3(或更高版本) 应用程序如何工作 完整的过程定义如下: 使用certificate.json向Google云进行 将data目录中的所有.json...
  • DataVec是Apache 2.0许可的库,用于机器学习ETL(提取,转换,加载)操作。 DataVec的目的是将原始数据转换为可用的矢量格式,然后将其提供给机器学习算法。 通过向该存储库贡献代码,您同意根据Apache 2.0许可提供...
  • 上一篇中我们已经完成了事件驱动的日志注入的事件驱动的部分,本篇我们继续介绍关于由事件驱动产生的增量 NSG Flow Log 如何进行 ETL 处理,然后流式的方式注入到 Data Explorer 分析引擎中。我们先来回顾一下整体...
  • SkaLogs ETL是专门针对日志和事件而设计的独特实时ETL。 核心功能: 集中式Logstash配置 基于常见预设模式的广泛列表的日志解析模拟 消费者流程:通过指导的工作流程进行摄取管道处理 摄取(来自特定的Kafka主题...
  • 概述 您可能有大量应用程序产生的JSON数据,您可能需要对这些JSON数据进行整理,去除...仅仅需要3步,就可以完成对海量JSON数据的处理,或者更为复杂的ETL流程。 第一步:JSON数据到阿里云OSS 利用各种手段,将JS...
  • kettle的使用和json格式文件的处理

    万次阅读 2018-03-30 20:31:08
    而是,如何使用Kettle处理Json文件,因为Kettle本身有一点点BUG,JsonInput不能直接处理Utf-8字符的json内容。所以,要学会变通一下。本例子使用的Kettle版本为7.1,下载网址:https://sourc...
  • SparkSQL ETL

    2019-10-14 15:41:13
    1)input:json日志 2)ETL:根据IP解析出 省份,城市 3)stat: 地区分布指标计算, 满足条件的才算,满足条件的赋值为1,不满足的赋值为0 (如下图) 将统计结果写入MySQL中。 (就比如说这个广告请求要满足 ...
  • 如何复用ETL的数据处理功能进行定制化服务开发 简介 众所周知,ETL是为数据报表而生,而报表往往是为领导层做决策提供数据支撑。面向领导编程往往是最能体现工作能力的。如何打造一个数据准确、实时性强的报表,就...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 4,991
精华内容 1,996
关键字:

etl处理json