Skip to content

Commit b4daef7

Browse files
authored
Merge branch 'main' into main
2 parents ae0f6f4 + 6e3b316 commit b4daef7

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

62 files changed

+33494
-39578
lines changed

.metadata/samples.json

+67-4
Original file line numberDiff line numberDiff line change
@@ -11990,9 +11990,9 @@
1199011990
],
1199111991
"thumbnails": [
1199211992
{
11993-
"type": "video",
11993+
"type": "image",
1199411994
"order": 100,
11995-
"url": "https://raw.githubusercontent.com/pnp/sp-dev-fx-webparts/refs/heads/main/samples/react-calendar/assets/react-calendar-categories.mp4",
11995+
"url": "raw.githubusercontent.com/pnp/sp-dev-fx-webparts/refs/heads/main/samples/react-calendar/assets/react-calendar-categories.png",
1199611996
"alt": "Calendar"
1199711997
},
1199811998
{
@@ -13795,6 +13795,69 @@
1379513795
}
1379613796
]
1379713797
},
13798+
{
13799+
"name": "pnp-sp-dev-spfx-web-parts-react-custom-localization",
13800+
"source": "pnp",
13801+
"title": "Custom Localization",
13802+
"shortDescription": "Shows how you can load localization files and use the localized strings if you have requirements to display localized text outside the normal SPFx/SPO processing",
13803+
"url": "https://github.com/pnp/sp-dev-fx-webparts/tree/main/samples/react-custom-localization",
13804+
"downloadUrl": "https://pnp.github.io/download-partial/?url=https://github.com/pnp/sp-dev-fx-webparts/tree/main/samples/react-custom-localization",
13805+
"longDescription": [
13806+
"Shows how you can load localization files and use the localized strings if you have requirements to display localized text outside the normal SPFx/SPO processing"
13807+
],
13808+
"creationDateTime": "2025-01-24",
13809+
"updateDateTime": "2025-01-24",
13810+
"products": [
13811+
"SharePoint"
13812+
],
13813+
"metadata": [
13814+
{
13815+
"key": "CLIENT-SIDE-DEV",
13816+
"value": "React"
13817+
},
13818+
{
13819+
"key": "SPFX-VERSION",
13820+
"value": "1.18.2"
13821+
}
13822+
],
13823+
"thumbnails": [
13824+
{
13825+
"name": "default-behavior.png",
13826+
"type": "image",
13827+
"order": 100,
13828+
"url": "https://raw.githubusercontent.com/pnp/sp-dev-fx-webparts/main/samples/react-custom-localization/assets/default-behavior.png",
13829+
"alt": "Web Part Preview"
13830+
},
13831+
{
13832+
"name": "page-translation-detection.png",
13833+
"type": "image",
13834+
"order": 101,
13835+
"url": "https://raw.githubusercontent.com/pnp/sp-dev-fx-webparts/main/samples/react-custom-localization/assets/page-translation-detection.png",
13836+
"alt": "Web Part Preview"
13837+
},
13838+
{
13839+
"name": "specific-language.png",
13840+
"type": "image",
13841+
"order": 102,
13842+
"url": "https://raw.githubusercontent.com/pnp/sp-dev-fx-webparts/main/samples/react-custom-localization/assets/specific-language.png",
13843+
"alt": "Web Part Preview"
13844+
}
13845+
],
13846+
"authors": [
13847+
{
13848+
"gitHubAccount": "brianpmccullough",
13849+
"pictureUrl": "https://github.com/brianpmccullough.png",
13850+
"name": "Brian McCullough"
13851+
}
13852+
],
13853+
"references": [
13854+
{
13855+
"name": "Build your first SharePoint client-side web part",
13856+
"description": "Client-side web parts are client-side components that run in the context of a SharePoint page. Client-side web parts can be deployed to SharePoint environments that support the SharePoint Framework. You can also use modern JavaScript web frameworks, tools, and libraries to build them.",
13857+
"url": "https://learn.microsoft.com/sharepoint/dev/spfx/web-parts/get-started/build-a-hello-world-web-part"
13858+
}
13859+
]
13860+
},
1379813861
{
1379913862
"name": "pnp-sp-dev-spfx-web-parts-react-custompropertypanecontrols",
1380013863
"source": "pnp",
@@ -27567,7 +27630,7 @@
2756727630
"This web part demonstrates Star Ratings capabilities to SharePoint News. The Ratings site collection feature provides Likes and Star Ratings, but SharePoint News provides only provides Likes. This web part can get or set ratings of the current page."
2756827631
],
2756927632
"creationDateTime": "2021-10-07",
27570-
"updateDateTime": "2023-11-09",
27633+
"updateDateTime": "2025-01-22",
2757127634
"products": [
2757227635
"SharePoint"
2757327636
],
@@ -27578,7 +27641,7 @@
2757827641
},
2757927642
{
2758027643
"key": "SPFX-VERSION",
27581-
"value": "1.18.0"
27644+
"value": "1.20.0"
2758227645
}
2758327646
],
2758427647
"thumbnails": [

samples/react-calendar/README.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ Each category has its own color that is generated in the load.
1010

1111
The Web Part checks the user's permissions for the View, Add, Edit, and Delete events.
1212

13-
![calendar](assets/react-calendar-categories.mp4)
13+
![calendar](assets/react-calendar-categories.png)
1414

1515
![calendar](assets/animatevideo.gif)
1616

Loading

samples/react-calendar/assets/sample.json

+2-2
Original file line numberDiff line numberDiff line change
@@ -31,9 +31,9 @@
3131
],
3232
"thumbnails": [
3333
{
34-
"type": "video",
34+
"type": "image",
3535
"order": 100,
36-
"url": "https://raw.githubusercontent.com/pnp/sp-dev-fx-webparts/refs/heads/main/samples/react-calendar/assets/react-calendar-categories.mp4",
36+
"url": "raw.githubusercontent.com/pnp/sp-dev-fx-webparts/refs/heads/main/samples/react-calendar/assets/react-calendar-categories.png",
3737
"alt": "Calendar"
3838
},
3939
{

samples/react-calendar/src/controls/Event/event.tsx

+25-20
Original file line numberDiff line numberDiff line change
@@ -816,49 +816,56 @@ export class Event extends React.Component<IEventProps, IEventState> {
816816
* @memberof Event
817817
*/
818818
private async returnExceptionRecurrenceInfo(recurrenceData: string) {
819-
const parser = new XMLParser();
819+
// Configure the XML parser
820+
const parser = new XMLParser({
821+
ignoreAttributes: false, // Include attributes in the parsed JSON
822+
attributeNamePrefix: "", // Do not prefix attributes with @
823+
isArray: (name) => ["rule", "repeat", "daily", "weekly", "monthly", "monthlyByDay", "yearly", "yearlyByDay"].includes(name), // Explicitly set nodes to be arrays
824+
});
825+
820826
try {
821-
// Parse the XML string into a JSON object
822-
const promise = parser.parse(recurrenceData);
823-
824-
const recurrenceInfo: any = await promise;
825-
if (recurrenceInfo != null) {
826-
let keys = Object.keys(recurrenceInfo.recurrence.rule[0].repeat[0]);
827+
// Parse the XML string
828+
const recurrenceInfo: any = parser.parse(recurrenceData);
829+
830+
// Check if parsed data contains expected structure
831+
if (recurrenceInfo?.recurrence?.rule?.[0]?.repeat?.[0]) {
832+
// Access repeat keys
833+
const repeat = recurrenceInfo.recurrence.rule[0].repeat[0];
834+
const keys = Object.keys(repeat);
835+
836+
// Supported recurrence types
827837
const recurrenceTypes = ["daily", "weekly", "monthly", "monthlyByDay", "yearly", "yearlyByDay"];
828-
for (var key of keys) {
829-
const rule = recurrenceInfo.recurrence.rule[0].repeat[0][key][0]['$'];
838+
839+
for (const key of keys) {
840+
const rule = repeat[key]?.[0]?.["$"];
841+
if (!rule) continue; // Skip if the rule is not present
842+
830843
switch (recurrenceTypes.indexOf(key)) {
831844
case 0:
832845
return this.parseDailyRule(rule);
833-
break;
834846
case 1:
835847
return this.parseWeeklyRule(rule);
836-
break;
837848
case 2:
838849
return this.parseMonthlyRule(rule);
839-
break;
840850
case 3:
841851
return this.parseMonthlyByDayRule(rule);
842-
break;
843852
case 4:
844853
return this.parseYearlyRule(rule);
845-
break;
846854
case 5:
847855
return this.parseYearlyByDayRule(rule);
848-
break;
849856
default:
850857
continue;
851858
}
852859
}
860+
} else {
861+
return "Invalid recurrence format";
853862
}
854-
855863
} catch (error) {
856-
// Handle parsing errors by rejecting the promise
864+
// Handle parsing errors
857865
throw new Error(`Error parsing recurrence data: ${error.message}`);
858866
}
859867
}
860868

861-
862869
/**
863870
*
864871
*
@@ -868,8 +875,6 @@ export class Event extends React.Component<IEventProps, IEventState> {
868875
*/
869876
public async returnRecurrenceInfo(startDate: Date, recurrenceData: string) {
870877
this.returnedRecurrenceInfo = { recurrenceData: recurrenceData, eventDate: startDate, endDate: moment().add(20, 'years').toDate() };
871-
//this.setState({ editRecurrenceSeries:false})
872-
//console.log(this.returnedRecurrenceInfo);
873878
}
874879

875880

samples/react-calendar/tsconfig.json

+3-5
Original file line numberDiff line numberDiff line change
@@ -25,11 +25,9 @@
2525
"webpack-env"
2626
],
2727
"lib": [
28-
"es5",
29-
"dom",
30-
"es2015.collection",
31-
"es2015.promise"
32-
]
28+
"es2016",
29+
"dom"
30+
],
3331
},
3432
"include": [
3533
"src/**/*.ts",

samples/react-carousel/package-lock.json

+3-3
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
{
2+
"name": "SPFx 1.18.2",
3+
"image": "docker.io/m365pnp/spfx:1.18.2",
4+
"customizations": {
5+
"vscode": {
6+
"extensions": [
7+
"editorconfig.editorconfig",
8+
"dbaeumer.vscode-eslint"
9+
]
10+
}
11+
},
12+
"forwardPorts": [
13+
4321,
14+
35729,
15+
5432
16+
],
17+
"portsAttributes": {
18+
"4321": {
19+
"protocol": "https",
20+
"label": "Manifest",
21+
"onAutoForward": "silent",
22+
"requireLocalPort": true
23+
},
24+
"5432": {
25+
"protocol": "https",
26+
"label": "Workbench",
27+
"onAutoForward": "silent"
28+
},
29+
"35729": {
30+
"protocol": "https",
31+
"label": "LiveReload",
32+
"onAutoForward": "silent",
33+
"requireLocalPort": true
34+
}
35+
},
36+
"postCreateCommand": "bash .devcontainer/spfx-startup.sh",
37+
"remoteUser": "node"
38+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
echo
2+
echo -e "\e[1;94mInstalling Node dependencies\e[0m"
3+
npm install
4+
5+
## commands to create dev certificate and copy it to the root folder of the project
6+
echo
7+
echo -e "\e[1;94mGenerating dev certificate\e[0m"
8+
gulp trust-dev-cert
9+
10+
# Convert the generated PEM certificate to a CER certificate
11+
openssl x509 -inform PEM -in ~/.rushstack/rushstack-serve.pem -outform DER -out ./spfx-dev-cert.cer
12+
13+
# Copy the PEM ecrtificate for non-Windows hosts
14+
cp ~/.rushstack/rushstack-serve.pem ./spfx-dev-cert.pem
15+
16+
## add *.cer to .gitignore to prevent certificates from being saved in repo
17+
if ! grep -Fxq '*.cer' ./.gitignore
18+
then
19+
echo "# .CER Certificates" >> .gitignore
20+
echo "*.cer" >> .gitignore
21+
fi
22+
23+
## add *.pem to .gitignore to prevent certificates from being saved in repo
24+
if ! grep -Fxq '*.pem' ./.gitignore
25+
then
26+
echo "# .PEM Certificates" >> .gitignore
27+
echo "*.pem" >> .gitignore
28+
fi
29+
30+
echo
31+
echo -e "\e[1;92mReady!\e[0m"
32+
33+
echo -e "\n\e[1;94m**********\nOptional: if you plan on using gulp serve, don't forget to add the container certificate to your local machine. Please visit https://aka.ms/spfx-devcontainer for more information\n**********"

0 commit comments

Comments
 (0)