2

I have class like this as below for design project where i am using this one to generate word document. the process is we are using ReactJS UI and .Net core and when the user click on button in UI we will be sending the request to API where we can download the word document.

public class DesignProject : PatchEntityProperties
{
    [Key, GraphQLNonNullType]
    public string ProjectNumber { get; set; }
    public string Name { get; set; }
    [Column(TypeName = "jsonb")]
    public ProjectSectionStatus SectionStatuses { get; set; }
    [ForeignKey("AshraeClimateZone"), GraphQLIgnore]
    public Guid? AshraeClimateZoneId { get; set; }
    public virtual AshraeClimateZone AshraeClimateZone { get; set; }
    public virtual ProjectPhase ProjectPhase { get; set; }
    [Column(TypeName = "jsonb")]
    public List<ProjectObject<LocalCode>> LocalCodes { get; set; } = new List<ProjectObject<LocalCode>>();
    .........
    ......
}

and project object is looks like as below

public class ProjectObject<T>
{
    public Guid? Id { get; set; }
    public T OriginalObject { get; set; }
    public T ModifiedObject { get; set; }

    [GraphQLIgnore, JsonIgnore]
    public T TargetObject
    {
        get
        {
            return ModifiedObject ?? OriginalObject;
        }
    }

}

and then i do have individual classes as mentioned in DesignProject class are like as below

public class LocalCode : AEIMaster
{
    public string Edition { get; set; }
    public string City { get; set; }
    public State State { get; set; }
    public Country Country { get; set; }        
}

i have few more classes and all are implementing AEIMaster interface used in word document generation and code is like as below

this is controller method where i am calling from UI

[Route("api/[controller]")]
[ApiController]
public class DesignProjectsController : ControllerBase
{
    private readonly APIDbContext _context;

    public DesignProjectsController(APIDbContext context)
    {
        _context = context;
    }

    [Authorize, HttpGet("{id}")]
    public async Task<ActionResult<DesignProject>> GetDesignProject(string id)
    {
        var designProject = await _context.DesignProjects.FindAsync(id);
        MemoryStream document = new DocumentGeneration().GenerateBasisOfDesign(designProject);

        return new InlineFileContentResult(document.ToArray(), "application/docx") { FileDownloadName = fileName };
    }
}

and then below is the code for DocumentGeneration class

    public MemoryStream GenerateBasisOfDesign(DesignProject designProject)
    {
        DesignProj = designProject;
        MemoryStream mem = new MemoryStream();

        using (WordprocessingDocument wordDoc = WordprocessingDocument.Create(mem, WordprocessingDocumentType.Document))
        {
            var mainDocumentPart = wordDoc.AddMainDocumentPart();
            Document doc = new Document();
            mainDocumentPart.Document = doc;
            doc.Body = new Body();

            Body body = wordDoc.MainDocumentPart.Document.Body;
            if (designProject.SectionStatuses.CodesAndGuidelinesSectionStatus != Design.Entities.Enums.ProjectSectionStage.NOT_APPLICABLE)
            {
                body.AppendChild(new Paragraph(new Run(new Text())));
                if ((designProject.LocalCodes?.Count ?? 0) > 0)
                {
                    body.AppendChild(new Paragraph(new Run(new Text())));
                    body.AppendChild(BuildSubHeaderPart("Applicable Local Codes", 2));
                    body.Append(RenderBulletedList(wordDoc, RenderRunList(designProject.LocalCodes.Select(s => s.TargetObject).Select(selector).ToList())));
                }
            }
            if(designProject.SectionStatuses.SpaceTypesSectionStatus != Design.Entities.Enums.ProjectSectionStage.NOT_APPLICABLE && (designProject.SpaceTypes?.Count ?? 0) > 0)
            {
                // use other classes which are derived from AEIMaster to generate a table and append that table to body 
            }
            if(Condition 3)
            { 
            }
            mainDocumentPart.Document.Body = body;
            mainDocumentPart.Document.Save();
            ApplyHeader(wordDoc);
        }
        return mem;
    }

i am looking to apply builder design pattern for this method and classes and i know it will separates the construction of complex object from its representation and i am not sure where to start with the above classes and methods.

Could any please suggest ideas or suggestions on this, many thanks in advance.

kumar jain
  • 93
  • 6
  • What and how are `Condition1` and `Condition2` defined? – Dai Jun 14 '20 at 02:22
  • I don't think using the Builder pattern is useful here because your code shows you only have a single scenario where you're creating objects. The Builder pattern is most useful when you need a *flexible* way to create objects - such as if you're making a redistributable library with a variety of use-cases. – Dai Jun 14 '20 at 02:23
  • BTW, you probably need to rewind your `MemoryStream` before you return it from `GenerateBasisOfDesign`. – Dai Jun 14 '20 at 02:23
  • i have added condition 1 and condition 2 here .. in each if condition i am generating table and appending that table to document – kumar jain Jun 14 '20 at 02:27
  • 2
    I’m voting to close this question because your question kinda sounds like _code improvement_ and/or _review_ and if so may be off-topic for SO. It _may_ be better suited for another SE site but be sure to read the relevant FAQ; and/or re-wording your question as necessary before cross-posting. [ask]. Good luck! –  Jun 14 '20 at 03:40

0 Answers0