9 people like it.

csproj-file parsing with Linq2Xml

This program reads all *.csproj-files from a path and then uses Linq2Xml to show data about the projects. This should be a good template for scripts to manage tons of c#-project files. F# and LINQ-to-XML is very powerful combination.

 1: 
 2: 
 3: 
 4: 
 5: 
 6: 
 7: 
 8: 
 9: 
10: 
11: 
12: 
13: 
14: 
15: 
16: 
17: 
18: 
19: 
20: 
21: 
22: 
23: 
24: 
25: 
26: 
27: 
28: 
29: 
30: 
//#r "System.Xml.dll" //for scripts or interactive
//#r "System.Xml.Linq.dll"
open System
open System.Xml.Linq
open System.IO

let getFiles = Directory.GetFiles(@"c:\projects\", "*.csproj", SearchOption.AllDirectories)
               |> Array.toSeq
 
let getProjectInfo (fname:string) = 
    let xn ns s = XName.Get(s,ns)
    let xml = XDocument.Load fname
    let xns = xn (xml.Root.Attribute(XName.Get("xmlns")).Value)

    let isSilverligthAssembly = xml.Descendants(xns "TargetFrameworkIdentifier")
                                |> (Seq.filter (fun p -> p.Value = "Silverlight") 
                                    >> Seq.isEmpty >> not)

    let outputPaths = xml.Descendants(xns "OutputPath") |> Seq.map(fun x -> x.Value)

    (fname, isSilverligthAssembly, outputPaths)

let showInfo projInfo =
    let name,sl,(outs:string seq) = projInfo
    match sl with
    | false -> Console.WriteLine("Assembly " + name + " outputs:") 
    | true -> Console.WriteLine("SL-assembly " + name + " outputs:")    
    outs |> Seq.iter(Console.WriteLine)

let test = getFiles |> Seq.map (getProjectInfo) |> Seq.iter(showInfo)
namespace System
namespace System.Xml
Multiple items
namespace System.Linq

--------------------
namespace Microsoft.FSharp.Linq
namespace System.IO
val getFiles : seq<string>

Full name: Script.getFiles
type Directory =
  static member CreateDirectory : path:string -> DirectoryInfo + 1 overload
  static member Delete : path:string -> unit + 1 overload
  static member EnumerateDirectories : path:string -> IEnumerable<string> + 2 overloads
  static member EnumerateFileSystemEntries : path:string -> IEnumerable<string> + 2 overloads
  static member EnumerateFiles : path:string -> IEnumerable<string> + 2 overloads
  static member Exists : path:string -> bool
  static member GetAccessControl : path:string -> DirectorySecurity + 1 overload
  static member GetCreationTime : path:string -> DateTime
  static member GetCreationTimeUtc : path:string -> DateTime
  static member GetCurrentDirectory : unit -> string
  ...

Full name: System.IO.Directory
Directory.GetFiles(path: string) : string []
Directory.GetFiles(path: string, searchPattern: string) : string []
Directory.GetFiles(path: string, searchPattern: string, searchOption: SearchOption) : string []
type SearchOption =
  | TopDirectoryOnly = 0
  | AllDirectories = 1

Full name: System.IO.SearchOption
field SearchOption.AllDirectories = 1
type Array =
  member Clone : unit -> obj
  member CopyTo : array:Array * index:int -> unit + 1 overload
  member GetEnumerator : unit -> IEnumerator
  member GetLength : dimension:int -> int
  member GetLongLength : dimension:int -> int64
  member GetLowerBound : dimension:int -> int
  member GetUpperBound : dimension:int -> int
  member GetValue : [<ParamArray>] indices:int[] -> obj + 7 overloads
  member Initialize : unit -> unit
  member IsFixedSize : bool
  ...

Full name: System.Array
val toSeq : array:'T [] -> seq<'T>

Full name: Microsoft.FSharp.Collections.Array.toSeq
val getProjectInfo : fname:string -> string * bool * seq<'a>

Full name: Script.getProjectInfo
val fname : string
Multiple items
val string : value:'T -> string

Full name: Microsoft.FSharp.Core.Operators.string

--------------------
type string = String

Full name: Microsoft.FSharp.Core.string
val xn : ('b -> 'c -> 'd)
val ns : 'b
val s : 'c
val xml : obj
val xns : (obj -> obj)
type Attribute =
  member Equals : obj:obj -> bool
  member GetHashCode : unit -> int
  member IsDefaultAttribute : unit -> bool
  member Match : obj:obj -> bool
  member TypeId : obj
  static member GetCustomAttribute : element:MemberInfo * attributeType:Type -> Attribute + 7 overloads
  static member GetCustomAttributes : element:MemberInfo -> Attribute[] + 15 overloads
  static member IsDefined : element:MemberInfo * attributeType:Type -> bool + 7 overloads

Full name: System.Attribute
val isSilverligthAssembly : bool
module Seq

from Microsoft.FSharp.Collections
val filter : predicate:('T -> bool) -> source:seq<'T> -> seq<'T>

Full name: Microsoft.FSharp.Collections.Seq.filter
val p : obj
val isEmpty : source:seq<'T> -> bool

Full name: Microsoft.FSharp.Collections.Seq.isEmpty
val not : value:bool -> bool

Full name: Microsoft.FSharp.Core.Operators.not
val outputPaths : seq<'a>
val map : mapping:('T -> 'U) -> source:seq<'T> -> seq<'U>

Full name: Microsoft.FSharp.Collections.Seq.map
val x : obj
val showInfo : string * bool * seq<string> -> unit

Full name: Script.showInfo
val projInfo : string * bool * seq<string>
val name : string
val sl : bool
val outs : seq<string>
Multiple items
val seq : sequence:seq<'T> -> seq<'T>

Full name: Microsoft.FSharp.Core.Operators.seq

--------------------
type seq<'T> = Collections.Generic.IEnumerable<'T>

Full name: Microsoft.FSharp.Collections.seq<_>
type Console =
  static member BackgroundColor : ConsoleColor with get, set
  static member Beep : unit -> unit + 1 overload
  static member BufferHeight : int with get, set
  static member BufferWidth : int with get, set
  static member CapsLock : bool
  static member Clear : unit -> unit
  static member CursorLeft : int with get, set
  static member CursorSize : int with get, set
  static member CursorTop : int with get, set
  static member CursorVisible : bool with get, set
  ...

Full name: System.Console
Console.WriteLine() : unit
   (+0 other overloads)
Console.WriteLine(value: string) : unit
   (+0 other overloads)
Console.WriteLine(value: obj) : unit
   (+0 other overloads)
Console.WriteLine(value: uint64) : unit
   (+0 other overloads)
Console.WriteLine(value: int64) : unit
   (+0 other overloads)
Console.WriteLine(value: uint32) : unit
   (+0 other overloads)
Console.WriteLine(value: int) : unit
   (+0 other overloads)
Console.WriteLine(value: float32) : unit
   (+0 other overloads)
Console.WriteLine(value: float) : unit
   (+0 other overloads)
Console.WriteLine(value: decimal) : unit
   (+0 other overloads)
val iter : action:('T -> unit) -> source:seq<'T> -> unit

Full name: Microsoft.FSharp.Collections.Seq.iter
val test : unit

Full name: Script.test

More information

Link:http://fssnip.net/8q
Posted:6 years ago
Author:Tuomas Hietanen
Tags: linq-to-xml , csproj , project , xlinq , xml