u01jmg3 / ics-parser
Requires
- php: >=5.6.40
- ext-mbstring: *
Requires (Dev)
- phpunit/phpunit: ^5|^9|^10
- dev-master
- v3.4.1
- v3.4.0
- v3.3.1
- v3.3.0
- v3.2.1
- v3.2.0
- v3.1.1
- v3.1.0
- v3.0.0
- v2.2.2
- v2.2.1
- v2.1.20
- v2.1.19
- v2.1.18
- v2.1.17
- v2.1.16
- v2.1.15
- v2.1.14
- v2.1.13
- v2.1.12
- v2.1.11
- v2.1.10
- v2.1.9
- v2.1.8
- v2.1.7
- v2.1.6
- v2.1.5
- v2.1.4
- v2.1.3
- v2.1.2
- v2.1.1
- v2.1.0
- v2.0.7
- v2.0.6
- v2.0.5
- v2.0.4
- v2.0.3
- v2.0.2
- v2.0.1
- 2.0.0
- 1.0.4
- 1.0.3
- v1.0.2
- v1.0.1
- v1.0.0
This package is auto-updated.
Last update: 2024-06-26 08:19:35 UTC
README
PHP ICS 解析器
安装
需求
- PHP 5 (≥ 5.6.40)
- 有效的 ICS (文件 .ics, .ical, .ifb)
- IANA, Unicode CLDR 或 Windows 时区
设置
- 安装 Composer
- 将以下依赖项添加到
composer.json
- ⚠️ 注意:Composer 中的所有者是
johngrogg
而不是u01jmg3
- ⚠️ 注意:Composer 中的所有者是
- 要访问最新稳定分支(
v3
),请使用以下命令-
要访问新功能,可以要求
dev-master
{ "require": { "johngrogg/ics-parser": "^3" } }
-
- 将以下依赖项添加到
运行测试
composer test
如何使用
如何实例化解析器
- 以示例脚本文档为指南,参考此代码
解析器将返回什么?
-
从 iCal 文件解析每个键/值对,为日历及其包含的每个事件创建关联数组。
-
还将注入
dtstart_tz
和dtend_tz
下的内容,以便在应用时区数据的情况下访问开始和结束日期。 -
尽可能使用
DateTime
对象,并返回。- ℹ️ 注意:解析器仅限于 相对日期格式,这可能会妨碍处理复杂的重复规则部分(例如,将
BYDAY
与BYSETPOS
结合)
// Dump the whole calendar var_dump($ical->cal); // Dump every event var_dump($ical->events());
- ℹ️ 注意:解析器仅限于 相对日期格式,这可能会妨碍处理复杂的重复规则部分(例如,将
-
还包括特殊的
{property}_array
数组,它们进一步解析键/值对的内容。// Dump a parsed event's start date var_dump($event->dtstart_array); // array (size=4) // 0 => // array (size=1) // 'TZID' => string 'America/Detroit' (length=15) // 1 => string '20160409T090000' (length=15) // 2 => int 1460192400 // 3 => string 'TZID=America/Detroit:20160409T090000' (length=36)
您是否使用 Outlook?
Outlook 有一个怪癖,它要求在您的请求头中设置用户代理字符串。
我们已为您注入默认用户代理字符串,如果尚未指定。
如果您希望提供自己的用户代理字符串,可以在创建 ICal 对象时使用 httpUserAgent
参数。
$ical = new ICal($url, array('httpUserAgent' => 'A Different User Agent'));
解析 iCal 资源时
解析 iCal/iCalendar/ICS 资源可能会带来一些挑战。一个挑战是规范是一个移动的目标;原始 RFC 在十年内只更新了四次。另一个挑战是供应商在解释规范时既自由(即:富有创意)又积极实现专有扩展。
然而,最直接阻碍高效解析的是事件的重复规则。这个库将原始日历解析成易于操作的内存模型。这需要将每个重复事件展开或分解。因此,每天发生一次的单个事件将在解析日历时生成新的事件实例($defaultSpan
限制了这一点)。要了解如何做到这一点,请查看调用图。
因此,整个日历必须逐行解析,首先加载到内存中。正如你所想象的,大型日历在展开时(即,所有重复规则都被评估时)往往会变得非常大。当旧日历每年变得更加庞大时,这种情况会加剧。
如果你只需要查看原始日历的一个窗口,这种限制尤其痛苦。如果你稍后要调用eventsFromInterval()
或 eventsFromRange()
,将整个完全展开的日历解析到内存中似乎是一种浪费。
在2018年底,#190 增加了在解析过程中非常早期就丢弃给定范围之外所有事件的功能,这以牺牲一些精度为代价(在那个点不会计算时区计算)。这大大减少了解析日历的总时间。同样,这也适用于内存消耗。前提是你事先知道你不在乎给定范围之外的事件。
比如说,你只对昨天的、今天的和明天的活动感兴趣。为了补偿在解析器决定保留或丢弃事件时,复杂的时区转换和计算尚未执行的事实,你可以将其设置为过滤 +-2d 而不是 +-1d。一旦完成,你就可以调用 eventsFromRange()
,加上 +-1d,以精确地获取你感兴趣的窗口中的活动。这就是变量 $filterDaysBefore
和 $filterDaysAfter
的作用。
在2019年第一季度,#213 通过在解析后立即丢弃 非重复 事件(如果它们不在模糊窗口内)来进一步提高了性能。这大大减少了大型日历的最大内存消耗。PHP默认情况下不会分配超过128MB堆栈,否则会因Fatal error: Allowed memory size of 134217728 bytes exhausted
而崩溃。不言而喻,在丢弃不匹配事件之前,必须先评估重复事件。
API
ICal
API
变量
名称 | 可配置 | 默认值 | 描述 |
---|---|---|---|
$alarmCount |
✖️ | N/A | 跟踪当前iCal源中警报的数量 |
$cal |
✖️ | N/A | 解析的日历 |
$defaultSpan |
☑️ | 2 |
用于无限期重复事件的年数 |
$defaultTimeZone |
☑️ | 系统默认值 | 启用自定义默认时区 |
$defaultWeekStart |
☑️ | MO |
表示一周第一天的两个字母表示 |
$disableCharacterReplacement |
☑️ | false |
切换是否禁用所有字符替换。如果 false ,则将花括号引号和其他特殊字符替换为它们的标准等效字符。这可能是一项代价高昂的操作! |
$eventCount |
✖️ | N/A | 跟踪当前iCal源中事件的数量 |
$filterDaysAfter |
☑️ | null |
当设置时,解析器将忽略现在之后大约这么多天内的所有事件。为了安全起见,建议您将过滤器窗口设置为比必要的 +/- 1 天更大。出于性能原因,此过滤器在执行任何日期和时间计算之前应用。因此,根据解析器和日历的时区设置,截止日期并未“校准”。然后您可以使用 $ical->eventsFromRange() 来精确缩小窗口。 |
$filterDaysBefore |
☑️ | null |
当设置时,解析器将忽略现在之前大约这么多天内的所有事件。有关详细信息,请参阅上面的 $filterDaysAfter 。 |
$freeBusyCount |
✖️ | N/A | 跟踪当前 iCal 提要中的空闲/忙碌计数 |
$httpBasicAuth |
✖️ | array() |
包含 HTTP 基本认证的用户名和密码 |
$httpUserAgent |
☑️ | null |
包含自定义 User Agent 字符串头 |
$httpAcceptLanguage |
✖️ | null |
包含自定义 Accept Language 请求头,例如 "en" 或 "de" |
$httpProtocolVersion |
✖️ | null |
包含自定义 HTTP 协议版本,例如 "1.0" 或 "1.1" |
$shouldFilterByWindow |
✖️ | false |
如果 $filterDaysBefore 或 $filterDaysAfter 已设置,则为 true |
$skipRecurrence |
☑️ | false |
切换是否跳过解析重复规则 |
$todoCount |
✖️ | N/A | 跟踪当前 iCal 提要中的待办事项数量 |
$windowMaxTimestamp |
✖️ | null |
如果设置了 $filterDaysBefore 或 $filterDaysAfter ,则根据此字段和 $windowMinTimestamp 定义的窗口过滤事件 |
$windowMinTimestamp |
✖️ | null |
如果设置了 $filterDaysBefore 或 $filterDaysAfter ,则根据此字段和 $windowMaxTimestamp 定义的窗口过滤事件 |
方法
方法 | 参数(s) | 可见性 | 描述 |
---|---|---|---|
__construct |
$files = false , $options = array() |
public |
创建 ICal 对象 |
initFile |
$file |
protected |
从文件初始化行 |
initLines |
$lines |
protected |
使用包含 iCal 内容每行的数组初始化解析器 |
initString |
$string |
protected |
从字符串初始化行 |
initUrl |
$url , $username = null , $password = null , $userAgent = null , $acceptLanguage = null |
protected |
从 URL 初始化行。接受用户名/密码组合进行 HTTP 基本认证、自定义 User Agent 字符串和接受的客户端语言 |
addCalendarComponentWithKeyAndValue |
$component , $keyword , $value |
protected |
将一个键和值对添加到 $this->cal 数组中 |
calendarDescription |
- | public |
返回日历描述 |
calendarName |
- | public |
返回日历名称 |
calendarTimeZone |
$ignoreUtc |
public |
返回日历时区 |
cleanCharacters |
$data |
protected |
将花括号引号和其他特殊字符替换为其标准等效字符 |
eventsFromInterval |
$interval |
public |
返回一个按给定字符串排序的事件数组 |
eventsFromRange |
$rangeStart = false , $rangeEnd = false |
public |
返回给定范围内的排序事件数组,如果在该范围内不存在事件,则返回空数组 |
events |
- | public |
返回事件数组 |
fileOrUrl |
$filename |
protected |
将整个文件或 URL 读取到数组中 |
filterValuesUsingBySetPosRRule |
$bysetpos , $valueslist |
protected |
通过应用 BYSETPOS RRule 过滤提供的值列表 |
freeBusyEvents |
- | public |
返回包含所有空闲/忙碌事件的数组 |
getDaysOfMonthMatchingByDayRRule |
$bydays , $initialDateTime |
protected |
查找一个月中所有匹配 RRULE 的 BYDAY 段的日期 |
getDaysOfMonthMatchingByMonthDayRRule |
$byMonthDays , $initialDateTime |
protected |
查找一个月中所有匹配 RRULE 的 BYMONTHDAY 段的日期 |
getDaysOfYearMatchingByDayRRule |
$byDays , $initialDateTime |
protected |
查找一年中所有匹配 RRULE 的 BYDAY 段的日期 |
getDaysOfYearMatchingByMonthDayRRule |
$byMonthDays , $initialDateTime |
protected |
找出一年中与RRULE的BYMONTHDAY部分匹配的所有日期 |
getDaysOfYearMatchingByWeekNoRRule |
$byWeekNums , $initialDateTime |
protected |
找出一年中与RRULE的BYWEEKNO部分匹配的所有日期 |
getDaysOfYearMatchingByYearDayRRule |
$byYearDays , $initialDateTime |
protected |
找出一年中与RRULE的BYYEARDAY部分匹配的所有日期 |
getDefaultTimeZone |
$forceReturnSystemDefault |
私有 |
如果已设置则返回默认时区,否则回退到系统默认时区 |
hasEvents |
- | public |
返回一个布尔值,表示当前日历是否有事件 |
iCalDateToDateTime |
$icalDate |
public |
从iCal日期时间格式返回一个DateTime 对象 |
iCalDateToUnixTimestamp |
$icalDate |
public |
从iCal日期时间格式返回一个Unix时间戳 |
iCalDateWithTimeZone |
$event , $key , $format = DATE_TIME_FORMAT |
public |
根据事件的TZID 返回适应日历时区的日期 |
doesEventStartOutsideWindow |
$event |
protected |
确定事件开始日期是否在$windowMinTimestamp / $windowMaxTimestamp 之外 |
isFileOrUrl |
$filename |
protected |
检查文件名是否存在作为文件或URL |
isOutOfRange |
$calendarDate , $minTimestamp , $maxTimestamp |
protected |
确定有效的iCalendar日期是否在给定的范围内 |
isValidCldrTimeZoneId |
$timeZone |
protected |
检查时区是否是有效的CLDR时区 |
isValidDate |
$value |
public |
检查日期字符串是否是有效的日期 |
isValidIanaTimeZoneId |
$timeZone |
protected |
检查时区是否是有效的IANA时区 |
isValidWindowsTimeZoneId |
$timeZone |
protected |
检查时区是否是公认的Windows(非CLDR)时区 |
isValidTimeZoneId |
$timeZone |
protected |
检查时区是否有效(IANA、CLDR或Windows) |
keyValueFromString |
$text |
public |
从iCal字符串中获取键值对 |
parseLine |
$line |
protected |
将iCal文件中的一行解析为令牌数组 |
mb_chr |
$code |
protected |
提供PHP 7.2的mb_chr() 的polyfill,它是chr()的多字节安全版本 |
escapeParamText |
$candidateText |
protected |
将不允许在参数文本中但允许在引号文本中的字符的文字用双引号括起来 |
parseDuration |
$date , $duration |
protected |
解析持续时间并将其应用于日期 |
parseExdates |
$event |
public |
解析要应用于事件的排除日期列表 |
processDateConversions |
- | protected |
使用时区处理日期转换 |
processEvents |
- | protected |
对从iCal文件中读取的所有事件执行管理任务 |
processRecurrences |
- | protected |
处理重复规则 |
reduceEventsToMinMaxRange |
protected |
将事件数量减少到定义的最小和最大范围 | |
removeLastEventIfOutsideWindowAndNonRecurring |
protected |
如果事件的开始日期在$windowMinTimestamp / $windowMaxTimestamp 所跨越的窗口之外,则移除最后一个事件(即最近解析的事件) |
|
removeUnprintableChars |
$data |
protected |
移除不可打印的ASCII和UTF-8字符 |
resolveIndicesOfRange |
$indexes , $limit |
protected |
从1到$limit 的范围内解析值 |
sortEventsWithOrder |
$events , $sortOrder = SORT_ASC |
public |
根据给定的排序顺序对事件进行排序 |
timeZoneStringToDateTimeZone |
$timeZoneString |
public |
基于包含时区名称的字符串返回一个DateTimeZone 对象 |
unfold |
$lines |
protected |
在解析之前展开iCal文件 |
常量
名称 | 描述 |
---|---|
DATE_TIME_FORMAT_PRETTY |
默认的漂亮日期时间格式 |
DATE_TIME_FORMAT |
默认日期时间格式 |
ICAL_DATE_TIME_TEMPLATE |
生成iCal日期时间的字符串模板 |
ISO_8601_WEEK_START |
一周的第一天,根据ISO-8601定义 |
RECURRENCE_EVENT |
用于隔离生成的重复事件 |
SECONDS_IN_A_WEEK |
一周中的秒数 |
TIME_FORMAT |
默认要使用的时间格式 |
TIME_ZONE_UTC |
UTC时区字符串 |
UNIX_FORMAT |
Unix时间戳日期格式 |
UNIX_MIN_YEAR |
Unix时间开始的那一年 |
Event
API(扩展了ICal
API)
方法
方法 | 参数(s) | 可见性 | 描述 |
---|---|---|---|
__construct |
$data = array() |
public |
创建Event对象 |
prepareData |
$value |
protected |
准备输出数据 |
printData |
$html = HTML_TEMPLATE |
public |
返回Event数据,排除HTML模板中的任何空白内容 |
snakeCase |
$input ,$glue = '_' ,$separator = '-' |
protected |
将给定输入转换为snake_case |
常量
名称 | 描述 |
---|---|
HTML_TEMPLATE |
用于打印内容的字符串模板 |
致谢
- Jonathan Goode(编程、错误修复、代码库增强、编码标准采用)
- s0600204(对RRULE支持的重大增强,许多错误修复和其他贡献)