Re: [go-nuts] Using nested struct to save master-detail POST request

2021-03-21 Thread Shulhan
On Sun, 21 Mar 2021 13:37:18 -0700 (PDT)
Hugh Myrie  wrote:

> I am able to decode the body of a POST request 
> using json.NewDecoder(r.Body)., then save the result to a database. 
> 
> Example:
> 
> type Product struct {
> IDint  `json:"id"`   
> Description  string  `json:"description"`
> Price   float64 `json:"price"`
> Packsize int `json:"packsize"`
> Count1 int `json:"count1"`
> Bin string `json:"bin"`
> Qoh int `json:"qoh"`
> }
> 
> items := []Product{}
> 
> err := json.NewDecoder(r.Body).Decode()
> if err != nil {
> http.Error(w, err.Error(), http.StatusBadRequest)
> fmt.Println("Error occurs here")
> log.Printf(err.Error())
> return
> }
> 
> How can I use a nested struct to produce two slices from an incoming 
> (master-detail) POST request, in the form:
> 
> [{receipt: 1, date: '01/01/2021', customer: 'Cash' , subtotal: 10.70,
>  detail: [{receipt: 1, description: 'item1', price: 2.00, qty: 2},
>   {receipt: 1, description: 'item2', price: 2.50, qty: 1},
>   {receipt: 1, description: 'item3', price: 4.20, qty: 1}]
> ]
> 
> I am trying to avoid sending two POST requests, master followed by
> detail.
> 

You can add new field with type is slice of struct inside the Product,
for example,

Details []ProductDetail `json:"detail"`

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/20210322112910.206bba4d%40inspiro.shul.localdomain.


Re: [go-nuts] No Generics - Type Binding on Imports

2021-03-21 Thread Ian Lance Taylor
On Sun, Mar 21, 2021 at 1:02 PM Martin Leiser  wrote:
>
> I think so. But How? Remember we need to do two things:
>
> - A way to define type parameters.
>
> - A way to bind the type parameters to concrete types at compile time

Thanks for the note.

I think that a generics proposal needs to do three things.  The third
is that it needs to describe which operations are permitted for a type
parameter.


> But after we named it "ElementType" we can get a hold of it and bind it in 
> the package we intend to use e.G. a "list of strings":
>
> import "container/list"  type ElementType string

This general kind of idea has been suggested quite a few times before.
Here are a few examples:

https://gist.github.com/PeterRK/41d4d3f54b8db55cd616403fd5a389f3
https://github.com/dotaheor/unify-Go-builtin-and-custom-generics/blob/master/use-package-as-gen.md
https://groups.google.com/g/golang-nuts/c/xKYXZpsWHus/m/SS4FKMBEAQAJ

There are others.


> Last features. If you need two different bindings in one package, say a list 
> of string and a list of int you may use:
>
> import "container/list" intlist  type ElementType = int
>
> import "container/list" stringlist type ElementType = string

What if I want to have a list of lists of strings?

What if I want to have a list of some unexported type that I defined
in this package?  That seems to require interweaving type definitions
and imports in ways that the language does not currently support.

With this proposal, how can I write a min function that works for any
integer type, including a user-defined integer type?  What happens if
I try to import a package that defines that Min function but I set the
argument type to some that does not support the < operator?

Thanks again.

Ian

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/CAOyqgcURm0uCGWPDQiyX_2FfGAon_snXKjn%3DmA_%3D1W1ScFc1Wg%40mail.gmail.com.


[go-nuts] Using nested struct to save master-detail POST request

2021-03-21 Thread Hugh Myrie
I am able to decode the body of a POST request 
using json.NewDecoder(r.Body)., then save the result to a database. 

Example:

type Product struct {
IDint  `json:"id"`   
Description  string  `json:"description"`
Price   float64 `json:"price"`
Packsize int `json:"packsize"`
Count1 int `json:"count1"`
Bin string `json:"bin"`
Qoh int `json:"qoh"`
}

items := []Product{}

err := json.NewDecoder(r.Body).Decode()
if err != nil {
http.Error(w, err.Error(), http.StatusBadRequest)
fmt.Println("Error occurs here")
log.Printf(err.Error())
return
}

How can I use a nested struct to produce two slices from an incoming 
(master-detail) POST request, in the form:

[{receipt: 1, date: '01/01/2021', customer: 'Cash' , subtotal: 10.70,
 detail: [{receipt: 1, description: 'item1', price: 2.00, qty: 2},
  {receipt: 1, description: 'item2', price: 2.50, qty: 1},
  {receipt: 1, description: 'item3', price: 4.20, qty: 1}]
]

I am trying to avoid sending two POST requests, master followed by detail.

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/1b5febdd-f4f0-4e56-86e9-a1fe0721d7ffn%40googlegroups.com.


[go-nuts] Code Review Checklist: Go Concurrency

2021-03-21 Thread Roman Leventov
I've created a list of possible concurrency-related bugs and gotchas in Go 
code: https://github.com/code-review-checklists/go-concurrency.

The idea of this list is to 
accompany https://github.com/golang/go/wiki/CodeReviewComments 
and https://golang.org/doc/articles/race_detector#Typical_Data_Races (my 
list actually refers to a couple of data races described in the list of 
"Typical Data Races").

Comments, corrections, additions are welcome!

If there are some core Go developers reading this, I would also like to 
know if you think some of the points from my list can be moved to 
https://github.com/golang/go/wiki/CodeReviewComments.

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/e4ec2bae-1c83-4ebd-95a9-db23f725d022n%40googlegroups.com.


[go-nuts] No Generics - Type Binding on Imports

2021-03-21 Thread Martin Leiser

Hi there

I am aware that the proposal to add generics has been accepted 
, so 
the discussion of whether or not Go will get generics is answered. For 
better or for worse.


I worked on a different approach since a few years, not very intensive, 
and in spite of this fact, I now want to tell you about:


Binding interface types on import 



See in: https://github.com/leiser1960/importbinding/blob/master/README.md

I did not speek up yet, because it simply was not ready for discussion 
in my eyes.



Why do I think the accepted proposal is not good enough?

Technically it seem sound and consistent to me and has all the bells and 
whistles you would expect. And all the Features. And close enough to the 
way other languages define generics.


So what do i dislike?

Hmmm... Let me answer another question first:

What do I love about Go?

Its *simplicity. *And Simplicity is Complicated 



And that is IMHO the problem of the accepted generics proposal, the lack 
of simplicity.


To explain this, let me start with a language design question:

    What is needed for adding "monomorphic generic types" to Go?

Go already has a polymorphic generic type mechanism: "interface types".

So you have to start from this (as the accepted proposal does) and add 
to things:


    - A way to define type parameters.

    - A way to bind the type parameters to concrete types at compile time

The accepted proposal does so by:

    1. Adding positional type parameters to type and function definitions

    2. Adding a syntax for binding concrete types to the type 
parameters on use of the types and functions.


With the proper brackets it is readable. And of course there are more 
goodies in the propsal such as:


    - An extension to the descriptive power of  "interface types".

    - type inference rules to eliminate the need of the additional type 
parameters in certain cases.


Both are great for functional libraries such as "sort.go", but does not 
help for container types such as "container/list.go".
And the proposal is long because any generic type mechanism is 
complicated to implement and tricky to integrate in the language.

This  is the obviously complicated part.

But the proposal lacks the simplicity and elegance of for example:

    - the way Go integrates inheriting method from a typ by simply 
omitting the attribute name in a struct definition


    - the way Go defines the types of numerical constant expressions 
for the purpose of type inference


incredibly simple to use and explain. No need for an additional 
syntactic element at all.

And completely different from the way other languages treat this.

The accepted proposal more or less follows the syntactic path taken 
since Ada, over C++ and Java and all the other languages.


It this good enough?

Can we do better?

I think so. But How? Remember we need to do two things:

    - A way to define type parameters.

    - A way to bind the type parameters to concrete types at compile time

Is suggest doing this on the package level, not the individual types or 
functions:


    1. Use named interface types as implicit type parameters of a package

    2. Bind the named types on import

With the first I simply mean any declaration of the form:

    type ElementType interface {}

e.g. The type Locker in sync.go.

You do not find such a declaration in "containter/list.go 
" . But it would be simple task 
to add such a line and replace all existing occurences of "interface{}" 
by "ElementType". Not changing the behaviour at all.


As a go proverb says: interface nothing says nothing 



But after we named it "ElementType" we can get a hold of it and bind it 
in the package we intend to use e.G. a "list of strings":


    import "container/list"  type ElementType string

augmenting the existing "import" clause by this type binding. We say:

    We bind (the binding) type "string" to (the bound type) 
"list.ElementType".


    We bind the type string to the type list.ElementType in the import 
of package list.


It is as simple as this.

But what does this mean?

It means two things:

    1. binding type must implement the bound type.

    2. the bound type is treated as if defined by:

            type BoundType BindingType

    in the imported package.

1. is trivial in our example, because interface{} is implemented by any 
time.


2. is trivial in our example, because "string" is a standard type.

The general case is not so trivial, think of the binding type being 
defined locally and private to the package.
I tried to give a semantic description in my definition in Binding 
interface types on import 
 but 
it is 

[go-nuts] Re: How to design HTTP request between HTTP servers

2021-03-21 Thread Brian Candler
Great - glad it's solved.  I was only going to suggest you insert more 
logging calls all over the place until you find the problem :-)

On Sunday, 21 March 2021 at 13:45:16 UTC Van Fury wrote:

>
> Hi,
>
> I have found the problem to the double PUT message being sent and have 
> solve it.
> Thanks for the help.
>
> A lot of lesson learnt from this exercise.
>
> On Sunday, March 21, 2021 at 1:47:07 PM UTC+2 Brian Candler wrote:
>
>> On Sunday, 21 March 2021 at 11:42:37 UTC Brian Candler wrote:
>>
>>> Also: somebody has to be responsible for closing the response.  You're 
>>> not explicitly returning an error from SendNFInstanceRegistration() to 
>>> HandleNFInstanceRegistration(), so the only way you can indicate that the 
>>> body is invalid is to return nil as the response pointer.
>>>
>>>
>> Sorry, I got that the wrong way round.  SendNFInstanceRegistration calls 
>> HandleNFInstanceRegistration, and you do return an error there.
>>
>> However, PutAndPatch calls SendNFInstanceRegistration, and you don't 
>> return an error.  The caller then checks resp.StatusCode, but doesn't 
>> account for the fact that there might have been some error, and so resp is 
>> nil.
>>
>> I would suggest that instead of returning a resp, you return bool "ok" 
>> which just says whether the request was successful or not.
>>
>

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/2f1f4950-9e35-42ff-adf0-7fe68fc28c94n%40googlegroups.com.


[go-nuts] Re: How to design HTTP request between HTTP servers

2021-03-21 Thread Van Fury

Hi,

I have found the problem to the double PUT message being sent and have 
solve it.
Thanks for the help.

A lot of lesson learnt from this exercise.

On Sunday, March 21, 2021 at 1:47:07 PM UTC+2 Brian Candler wrote:

> On Sunday, 21 March 2021 at 11:42:37 UTC Brian Candler wrote:
>
>> Also: somebody has to be responsible for closing the response.  You're 
>> not explicitly returning an error from SendNFInstanceRegistration() to 
>> HandleNFInstanceRegistration(), so the only way you can indicate that the 
>> body is invalid is to return nil as the response pointer.
>>
>>
> Sorry, I got that the wrong way round.  SendNFInstanceRegistration calls 
> HandleNFInstanceRegistration, and you do return an error there.
>
> However, PutAndPatch calls SendNFInstanceRegistration, and you don't 
> return an error.  The caller then checks resp.StatusCode, but doesn't 
> account for the fact that there might have been some error, and so resp is 
> nil.
>
> I would suggest that instead of returning a resp, you return bool "ok" 
> which just says whether the request was successful or not.
>

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/68e6ba3c-df54-43b9-b7e1-f6574d3153cen%40googlegroups.com.


[go-nuts] Re: How to design HTTP request between HTTP servers

2021-03-21 Thread Van Fury

Hi,
Line line 147 of register.go is status code check in the second for loop 
but now solved.

if res.StatusCode != http.StatusNoContent {

But i still could not find out why the SendNFInstanceRegistration() message 
is send twice even though i have check
the responses here

fmt.Print("status:", status)

if status == http.StatusOK {
logrus.Println("PCF Profile Update SUCCESS")
} else if status == http.StatusCreated {
logrus.Println("PCF Profile Registration SUCCESS")
} else {

logrus.Println(fmt.Errorf("Wrong status code returned by nrf %d", status))
}

Response codes:
status:201INFO[] PCF Profile Registration SUCCESS 
status:200INFO[] PCF Profile Update SUCCESS  

I have check all errors and this is the final code but the problem now is 
the PUT message being sent twice. 
Could you help find out what am doing wrong
func SendNFInstanceRegistration() (int32, string, *http.Response, error) {

var (
profile Profile
errerror
)
profilebytes, err := ioutil.ReadFile("./profile.json")
if err != nil {
logrus.Println("Cannot read json file")
}
// unmarshall it
err = json.Unmarshal(profilebytes, )
if err != nil {
logrus.Errorf("Read File profile Unmarshal failed %s", err.Error())
}

profile.NfInstanceId = contx.ID
id := contx.ID

locProfilebytes, err := json.Marshal(profile)
if err != nil {
logrus.Error(err)
}

locVarNRFUrl := NewConfig.BasePath + "/nf-instances/" + id

htbt, contentLoc, resp, err := 
HandleNFInstanceRegistration(locProfilebytes, locVarUrl)
if err != nil {
logrus.Error("could not register profile")
return htbt, contentLoc, resp, err
}

if resp == nil {
logrus.Error(err)
return htbt, contentLoc, resp, err
}

status := resp.StatusCode

fmt.Print("status:", status)

if status == http.StatusOK {
logrus.Println("Profile Update SUCCESS")
} else if status == http.StatusCreated {
logrus.Println("Profile Registration SUCCESS")
} else {

logrus.Println(fmt.Errorf("Wrong status code returned %d", status))
}

heartBeatTimer := htbt
return heartBeatTimer, contentLoc, resp, nil

}

func HandleNFInstanceRegistration(nfprofilebyte []byte, VarPath string) 
(int32, string, *http.Response, error) {

var (
// Set client and set url
localVarHTTPMethod = http.MethodPut
nfprofile  models.NfProfile
heartBeatTimer int32
contentloc string
)

req, err := http.NewRequest(localVarHTTPMethod, VarPath, 
bytes.NewBuffer(nfprofilebyte))
if err != nil {
logrus.Error(err)
}
req.Close = true
req.Header.Set("Content-Type", "application/json")
req.Header.Set("Accept", "application/json")


backoff := 1
for {

res, err := transport.Client.Do(req) //Use for dev
if err != nil || res == nil {
logrus.Println("trying to register profile ...")
backoff *= 2
if backoff > 20 {
backoff = 20
}
time.Sleep(time.Duration(backoff) * time.Second)
continue
}

if res == nil {
logrus.Errorf("Registration failed %s", err.Error())
return heartBeatTimer, contentloc, res, err
}

defer func() {
if resCloseErr := res.Body.Close(); resCloseErr != nil {
logrus.Errorf("RegisterNFInstance response body cannot 
close: %+v", resCloseErr)
}
}()

bodybytes, err := ioutil.ReadAll(res.Body)
if err != nil {
logrus.Error(err)
return heartBeatTimer, contentloc, res, err
}

err = json.Unmarshal(bodybytes, )
if err != nil {
logrus.Errorf("Profile Unmarshal failed %s", err.Error())
return heartBeatTimer, contentloc, res, err
}

heartBeatTimer = nfprofile.HeartBeatTimer
contentloc := res.Header.Get("Location")

return heartBeatTimer, contentloc, res, nil
}
}


func SendHeartbeat(ContentLocation string) (response *http.Response, err 
error) {

// Preapare Heart-Beat message
patchitem := []models.PatchItem{
models.PatchItem{
Op:"replace",
Path:  "/load",
From:  ContentLocation,
Value: "REG",
}
}

patchitembytes, err := json.Marshal(patchitem)
if err != nil {
logrus.Error(err)
}

req, err := http.NewRequest("PATCH", ContentLocation, 
bytes.NewBuffer(patchitembytes))
req.Header.Set("Content-Type", "application/json-patch+json")

response, err = transport.Client.Do(req) // for dev
if err != nil {
logrus.Debug("Heart-Beat Request FAILED")
return response, err
}

defer response.Body.Close()

status := response.StatusCode
if status == 

[go-nuts] Re: How to design HTTP request between HTTP servers

2021-03-21 Thread Brian Candler
On Sunday, 21 March 2021 at 11:42:37 UTC Brian Candler wrote:

> Also: somebody has to be responsible for closing the response.  You're not 
> explicitly returning an error from SendNFInstanceRegistration() to 
> HandleNFInstanceRegistration(), so the only way you can indicate that the 
> body is invalid is to return nil as the response pointer.
>
>
Sorry, I got that the wrong way round.  SendNFInstanceRegistration calls 
HandleNFInstanceRegistration, and you do return an error there.

However, PutAndPatch calls SendNFInstanceRegistration, and you don't return 
an error.  The caller then checks resp.StatusCode, but doesn't account for 
the fact that there might have been some error, and so resp is nil.

I would suggest that instead of returning a resp, you return bool "ok" 
which just says whether the request was successful or not.

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/5a3230da-a3ab-40a2-a31a-f80743730d70n%40googlegroups.com.


[go-nuts] Re: How to design HTTP request between HTTP servers

2021-03-21 Thread Brian Candler
On Sunday, 21 March 2021 at 11:20:40 UTC Van Fury wrote:

> After this , the PATCH message is send OK but when server B stop running,
> server A break, complain g about the status check in the PATCH for loop
>
> status204ERRO[0350] Patch "
> http://127.0.0.1:9090/nnrf-nfm/v1/nf-instances/6ba7b810-9dad-11d1-80b4-00c04fd430c9":
>  
> dial tcp 127.0.0.1:9090: connect: connection refused 
> panic: runtime error: invalid memory address or nil pointer dereference
> [signal SIGSEGV: segmentation violation code=0x1 addr=0x0 pc=0xe6aa92]
>
> goroutine 47 [running]:
> PutAndPatch()
> register.go:147 +0x1d2
> exit status 2
>
>
Can you show the code at line 147 of register.go, with two or three lines 
of context either side?

My guess is that your problem is here:

interval, cl, resp = SendNFInstanceRegistration()

*status := resp.StatusCode*

or here:

   htbt, contentLoc, resp, err := 
HandleNFInstanceRegistration(locProfilebytes, locVarUrl)
if err != nil {
logrus.Error("Server A could not register profile")
}

*status := resp.StatusCode*

In either case, what happens if resp is nil?  You have checked for the case 
of err != nil, but you only make a log message - and then continue blithely 
on as if everything was successful.  But in the case of error, resp is 
likely to be nil, and you can't dereference a nil pointer.  That's what 
causes the panic.

Also: somebody has to be responsible for closing the response.  You're not 
explicitly returning an error from SendNFInstanceRegistration() to 
HandleNFInstanceRegistration(), so the only way you can indicate that the 
body is invalid is to return nil as the response pointer.


interval, cl, resp = SendNFInstanceRegistration()
*if resp == nil {*
... log if you like
*return ...*
*}*
*defer resp.Body.Close()*
status := resp.StatusCode
 continue to parse the response
 
Personally I think it would be cleaner to return an explicit "err", as it's 
consistent with the normal conventions.

You still aren't checking the error response from json.Unmarshal(bodybytes, 
).  If the JSON parsing fails then you'll get a zero response for 
the timer interval, and a ticker with a zero interval will cause a panic.

I think I'll leave it with you now.  In short: check errors everywhere; 
take the correct action on error - which might just be returning the error 
to the caller, but don't just ignore it and carry on as if everything was 
OK.  And make sure things are closed that need to be closed.

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/3edf6058-6e38-4cf4-841c-c4be7c9dc949n%40googlegroups.com.


[go-nuts] Re: How to design HTTP request between HTTP servers

2021-03-21 Thread Brian Candler
On Saturday, 20 March 2021 at 19:19:53 UTC Van Fury wrote:

> OK, if I understand you correctly, the outer for loop is not needed and 
> that
> there should be two for loops.
> the first for loop does step 1,2 and 3 and then "break" out of the loop 
> when valid response is received
> and then set the "interval".
> The second for loop start a for _ := range ticker.C loop and also break 
> out when there is a PATCH failure response.
>
>
And then you'll need an outer for loop around that, so that the PATCH 
failure response causes you to restart at step 1.

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/e3c27698-bf2c-43c4-b2e4-6fe3d802fe5cn%40googlegroups.com.


[go-nuts] Re: How to design HTTP request between HTTP servers

2021-03-21 Thread Van Fury
Hi, 

This is what i have done so far but still having problems.
When server A starts and server B is not available, it retry but if server 
B start running,
sever A sends the PUT message in the SendNFInstanceRegistration(). When i 
print
the status code in SendNFInstanceRegistration() i get 

status:201 INFO[0014] Server A Profile Registration To SUCCESS  
status:200 INFO[0014] Server A Profile Update SUCCESS 

After this , the PATCH message is send OK but when server B stop running,
server A break, complain g about the status check in the PATCH for loop

status204ERRO[0350] Patch 
"http://127.0.0.1:9090/nnrf-nfm/v1/nf-instances/6ba7b810-9dad-11d1-80b4-00c04fd430c9":
 
dial tcp 127.0.0.1:9090: connect: connection refused 
panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x0 pc=0xe6aa92]

goroutine 47 [running]:
PutAndPatch()
register.go:147 +0x1d2
exit status 2

Am expecting the "break" in the PATCH message to restart the PUT message 
again until server B is up again

Here is what i have done so far 


// Send PUT message
func SendNFInstanceRegistration() (int32, string, *http.Response) {

var profile Profile

profilebytes, err := ioutil.ReadFile("./profile.json")
if err != nil {
logrus.Println("Cannot read json file")
}
// unmarshall it
err = json.Unmarshal(profilebytes, )
if err != nil {
logrus.Print(err)
}

pcfprofile.NfInstanceId = contx.ID
id := contx.ID

locProfilebytes, err := json.Marshal(profile)
if err != nil {
logrus.Println(err)
}

locVarUrl := NewConfig.BasePath + "/nf-instances/" + id

htbt, contentLoc, resp, err := 
HandleNFInstanceRegistration(locProfilebytes, locVarUrl)
if err != nil {
logrus.Error("Server A could not register profile")
}

status := resp.StatusCode

fmt.Print("status:", status)

if status == http.StatusOK {
logrus.Println("Server A Profile Update SUCCESS")
} else if status == http.StatusCreated {
logrus.Println("Server A Profile Registration To SUCCESS")
} else {

logrus.Println(fmt.Errorf("Wrong status code returned by Server B 
%d", status))
}

heartBeatTimer := htbt
return heartBeatTimer, contentLoc, resp

}

func HandleNFInstanceRegistration(nfprofilebyte []byte, VarPath string) 
(int32, string, *http.Response, error) {

var (
// Set client and set url
localVarHTTPMethod = http.MethodPut
nfprofile  Profile
heartBeatTimer int32
contentloc string
)

req, err := http.NewRequest(localVarHTTPMethod, VarPath, 
bytes.NewBuffer(nfprofilebyte))
if err != nil {
logrus.Error(err)
}
req.Close = true
req.Header.Set("Content-Type", "application/json")
req.Header.Set("Accept", "application/json")

backoff := 1
for {
res, err := transport.Client.Do(req) //Use for dev
if err != nil || res == nil {
logrus.Println("Server A trying to register profile ...")
backoff *= 2
if backoff > 20 {
backoff = 20
}
time.Sleep(time.Duration(backoff) * time.Second)
continue
}

defer func() {
if resCloseErr := res.Body.Close(); resCloseErr != nil {
logrus.Errorf("response body cannot close: %+v", 
resCloseErr)
}
}()

bodybytes, err := ioutil.ReadAll(res.Body)
//localVarHTTPResponse.Body.Close()
if err != nil {
logrus.Error(err)
return heartBeatTimer, contentloc, res, err
}

json.Unmarshal(bodybytes, )

heartBeatTimer = nfprofile.HeartBeatTimer
contentloc := res.Header.Get("Location")

return heartBeatTimer, contentloc, res, nil
}
}


// PATCH message
// func SendHeartbeat(ContentLocation string) (response *http.Response, err 
error) {

patchitem := []models.PatchItem{
models.PatchItem{
Op:"replace",
Path:  "/load",
From:  ContentLocation,
Value: "REG,
}
}

patchitembytes, err := json.Marshal(patchitem)
if err != nil {
logrus.Error(err)
}

req, err := http.NewRequest("PATCH", ContentLocation, 
bytes.NewBuffer(patchitembytes))
req.Header.Set("Content-Type", "application/json-patch+json")

response, err = transport.Client.Do(req) // for dev
if err != nil {
logrus.Debug("Server A Heart-Beat Request FAILED")
return response, err
}

defer response.Body.Close()

status := response.StatusCode
if status == http.StatusNoContent {
logrus.Info("Heart-Beat Message SUCCESS")

} else if status == http.StatusNotFound {
logrus.Println("Heart-Beat Message FAILED")
}

return response, err
}



func PutAndPatch() {

var interval int32
var